Background Tasks

RSS for tag

Request the system to launch your app in the background to run tasks using Background Tasks.

Posts under Background Tasks tag

137 Posts

Post

Replies

Boosts

Views

Activity

Background Tasks Resources
General: Forums subtopic: App & System Services > Processes & Concurrency Forums tag: Background Tasks Background Tasks framework documentation UIApplication background tasks documentation ProcessInfo expiring activity documentation Using background tasks documentation for watchOS Performing long-running tasks on iOS and iPadOS documentation WWDC 2020 Session 10063 Background execution demystified — This is critical resource. Watch it! [1] WWDC 2022 Session 10142 Efficiency awaits: Background tasks in SwiftUI WWDC 2025 Session 227 Finish tasks in the background — This contains an excellent summary of the expected use cases for each of the background task types. iOS Background Execution Limits forums post UIApplication Background Task Notes forums post Testing and Debugging Code Running in the Background forums post Share and Enjoy — Quinn “The Eskimo!” @ Developer Technical Support @ Apple let myEmail = "eskimo" + "1" + "@" + "apple.com" [1] Sadly the video is currently not available from Apple. I’ve left the link in place just in case it comes back.
0
0
4.5k
Nov ’25
Maximum number of BGContinuedProcessingTasks?
I have a weird situation arising in my app where calling BGTaskScheduler.shared.submit(request) seems to fail silently, without raising any of the BGTaskScheduler.Error's. Here's what's happening. A user registers and submits 5 BGContinuedProcessingTask's, with different ID's using the wildcard. When trying to submit the 6th task like this: try bgTask.submit() //submit task isCreatingBGTask = false // toggle ProgressView off dismiss() //Dismiss the sheet The sheet will dismiss, but the device never gives the haptic feedback, and the task is not visible in the notification centre. Having a maximum number of running tasks makes sense, but why isn't it raising the error BGTaskScheduler.Error(.immediateRunIneligible). It also doesn't seem like there's a way to query the tasks that are in progress (at least I couldn't find a way). So for now I'll just track my own tasks manually, and prevent submission at 5 tasks, but I'm wondering what would happen if another app had 2 tasks going, and then my user tries to submit 3 or something like that.
0
0
16
10h
PHAssetResourceUploadJobChangeRequest doesn't upload iCloud-optimized photos — is this expected?
I'm implementing PHBackgroundResourceUploadExtension to back up photos and videos to our cloud storage service. During testing, I observed that iCloud-optimized photos (where the full-resolution original is stored in iCloud, not on device) do not upload. The upload job appears to silently skip these assets. Questions: Is this behavior intentional/documented? I couldn't find explicit mention of this limitation. If the device only has the optimized/thumbnail version locally, does the system: - Automatically download the full-resolution asset from iCloud before uploading? - Skip the asset entirely? - Return an error via PHAssetResourceUploadJobChangeRequest? For a complete backup solution, should we: - Pre-fetch full-resolution assets using PHAssetResourceManager.requestData(for:options:) before creating upload jobs? - Use a hybrid approach (this extension for local assets + separate logic for iCloud-only assets)? Environment: iOS 26, Xcode 18
1
1
247
2d
How to upload large videos with PHAssetResourceUploadJobChangeRequest?
I'm implementing a PHBackgroundResourceUploadExtension to back up photos and videos from the user's library to our cloud storage service. Our existing upload infrastructure uses chunked uploads for large files (splitting videos into smaller byte ranges and uploading each chunk separately). This approach: Allows resumable uploads if interrupted Stays within server-side request size limits Provides granular progress tracking Looking at the PHAssetResourceUploadJobChangeRequest.createJob(destination:resource:) API, I don't see a way to specify byte ranges or create multiple jobs for chunks of the same resource. Questions: Does the system handle large files (1GB+) automatically under the hood, or is there a recommended maximum file size for a single upload job? Is there a supported pattern for chunked/resumable uploads, or should the destination URL endpoint handle the entire file in one request? If our server requires chunked uploads (e.g., BITS protocol with CreateSession → Fragment → CloseSession), is this extension the right mechanism, or should we use a different approach for large videos? Any guidance on best practices for large asset uploads would be greatly appreciated. Environment: iOS 26, Xcode 18
5
1
911
2d
How to reliably debug PHBackgroundResourceUploadExtension during development?
I'm developing a PHBackgroundResourceUploadExtension and finding it difficult to debug because the system controls when the extension launches. Current experience: The extension starts at unpredictable times (anywhere from 1 minute to several hours after photos are added) By the time I attach the debugger, the upload may have already completed or failed Breakpoints in init() or early lifecycle methods are often missed Questions: Is there a way to force-launch the extension during development (similar to how we can manually trigger Background App Refresh in Xcode)? Are there any launch arguments or environment variables that put the extension in a debug/eager mode? I tried taking photos/videos, but this doesn't trigged app extension in all cases. Any tips for improving the debug cycle would be greatly appreciated. Environment: iOS 26, Xcode 18
2
1
707
3d
Network Socket Background Task
Hello everyone, I have developed an app that is a local networking monitor app for a specific building automation protocol. I have searched the forum and I think I have found some older posts regarding this topic but I could not figure out if my issue falls under the same category. So my app allows the user to connect to local protocol devices, and start a monitor session where they can see incoming/outgoing packets. The connections are UDP or TCP and require opening a socket. Currently, backgrounding the app will make the OS terminate the socket connection, therefore ending the monitor, even if the app is backgrounded by user, to let's say, perform some other task in their phone. I have several requests from users to improve the app by allowing the monitor to continue while the app is backgrounded. However, by reading the relevant documents, I have found this to be almost impossible in iOS app. I have considered: Remote Push Notifications (APNs): The app operates on LAN so this is not an option, since I do not have an infrastructure to somehow send notifications to keep app process alive. Background Tasks (BGTaskScheduler): Not my case, since I do not want periodic execution. The app requires continuous socket listening. VoIP, VPN, or Audio Background Modes: My app does not fall under any of these categories, even though this would solve my situation. By searching around a bit more, I might be able to use either BGProcessingTask, which would allow my app at least to run for some minutes and show the user that they have to foreground it in order to not stop the monitor process, or maybe even App Intents framework. Has anyone faced similar requirement for their app? Any tip or point to a direction I should investigate more? Thanks, Nikos
0
0
27
3d
Is the Dock "Running in Background" indicator supposed to trigger for registered launchd jobs with no live process on macOS 27?
I just noticed something on macOS 27 beta 1 and I'm not sure if it's a bug or just how the new feature works. After quitting an app with Cmd+Q, the Dock keeps showing the gray dot with the "Running in Background" message. So I checked — ps aux shows nothing running for the app at all. The only trace is its auto-updater job in launchctl list (com.anthropic.claudefordesktop.ShipIt), which is registered but has no PID, so it's not actually executing anything. Out of curiosity I tried Discord and got the exact same thing (com.discord.discord.ShipIt), so this probably happens with any Electron app that uses the Squirrel updater. Is this intended behavior? Trying to understand if the indicator reflects registered background items (and not just live processes) so I know what to expect for Electron-based apps.
0
0
49
4d
Reliable network request from a terminated, PushKit-launched app during CXEndCallAction
Environment: iOS 18.7.8, CallKit + PushKit VoIP. On VoIP push we call reportNewIncomingCall and show the system CallKit UI. Goal: When the user declines from the CallKit UI, send a single HTTPS POST to our backend in realtime, across all app states. Problem: Foreground and backgrounded states work. When the app is terminated (system-evicted or user-force-quit), the push launches the app, CallKit shows, and we receive CXEndCallAction — but the network request doesn't reliably leave the device. The process is suspended/terminated moments after the action returns. Tried: URLSession.shared dataTask inside CXEndCallAction — frozen with the app; resumes only on next foreground launch. beginBackgroundTask(withName:) around the request — insufficient when terminated. Background URLSession (.background, isDiscretionary = false, sessionSendsLaunchEvents = true, uploadTask(fromFile:), body staged in Caches, held briefly with a task assertion). Reliable when backgrounded; still unreliable/delayed when terminated, especially after force-quit. Questions: Is reliable, near-realtime client network delivery from a terminated, PushKit-launched app possible, or is this an inherent platform constraint? If it's a constraint, is the recommended pattern to treat the decline as best-effort and make the server authoritative (e.g., ring timeout)? Any official references? Does force-quit vs. system termination change background-execution / background-URLSession guarantees, and is there a supported approach for force-quit specifically? Any API we missed (e.g., a sanctioned way to extend runtime during CXEndCallAction, or background-URLSession scheduling guarantees for VoIP) that makes this realtime-reliable?
0
0
38
6d
Background Assets: Downloaded .aar not working — "bundle record couldn't be looked up" error (-10814)
Platform: iOS 26 (23E254) Xcode: 26.0 Reproduces on: Debug builds AND TestFlight Summary: I'm using Apple-Hosted Managed Background Assets with on-demand download policy. The .aar archives download successfully (correct file size, status = downloaded), but the contents are never extracted into the asset pack namespace. AssetPackManager.shared.contents(at:) returns fileNotFound for all path variants, and url(for: FilePath(".")) returns a URL that exists but contains zero children. Root Cause from Sysdiagnose: The backgroundassets.user daemon logs reveal this error on every download attempt: A bundle record couldn't be looked up for the application identifier "AtlasDrift.SnapTrail": Error Domain=NSOSStatusErrorDomain Code=-10814 "(null)" UserInfo={_LSFile=LSBindingEvaluator.mm, _LSLine=1973, _LSFunction=runEvaluator} Error code -10814 is kLSApplicationNotFoundErr. The BA daemon downloads the .aar blob, then attempts to find the app bundle via LaunchServices to locate the extension for extraction — but the LS lookup fails. Without the extension, extraction never occurs. Verified Configuration Everything matches the documentation and WWDC sessions: Extension embedded at SnapTrail.app/Extensions/BackgroundDownloadExtension.appex Bundle IDs: App = AtlasDrift.SnapTrail, Extension = AtlasDrift.SnapTrail.BackgroundDownloadExtension (correct parent-child pattern) Extension point: com.apple.background-asset-downloader-extension Product type: com.apple.product-type.extensionkit-extension Protocol: StoreDownloaderExtension from StoreKit (for Apple-hosted packs) App group: group.AtlasDrift.SnapTrail (matching in both app and extension entitlements) Info.plist keys: BAAppGroupID, BAHasManagedAssetPacks = YES BAUsesAppleHosting = YES (no BAInitialDownloadRestrictions or other BA keys) .aar Packaging Archives built with xcrun ba-package from the Assets directory. Manifest format: { "assetPackID": "ireland", "downloadPolicy": { "onDemand": {} }, "fileSelectors": [{ "directory": "POIRegions/ireland/IR" }], "platforms": ["iOS"] } Uploaded via App Store Connect API with assetType: "ASSET". Diagnostic Observations AssetPackManager.shared.assetPack(withID:) returns valid metadata (correct download size) ensureLocalAvailability(of:) completes without error assetPackIsAvailableLocally(withID:) returns true url(for: FilePath(".")) returns a URL that exists but has zero children (empty namespace) contents(at:) returns fileNotFound for all path variants tested The extension never runs — breadcrumb file written in init() is never created The -10814 error appears in daemon logs for every download cycle Questions Has anyone successfully used Apple-Hosted Managed Background Assets on iOS 26 beta? Is the daemon's LaunchServices integration known to be broken in this seed? Is there anything about the bundle identifier format or provisioning profile setup that could cause the BA daemon's LS lookup to fail, even though the app installs and runs fine otherwise? Are there any additional Info.plist keys or entitlements beyond what's documented that might be required for the daemon to locate the app bundle? Any guidance would be appreciated. I've filed a Feedback report with the full sysdiagnose attached.
2
0
426
1w
Background Termination Investigation
Hello, We are currently investigating an issue where our app is being terminated by the system while running in the background. At the moment, the app does not perform any significant background activity, and memory usage remains relatively low (approximately 150–200 MB). Despite this, the app is still being terminated in the background, even under conditions where other apps appear to remain active. From our investigation so far, the issue does not appear to be related to: High memory consumption Explicit background task misuse Application crashes on our side For additional context, we had previously used silent push notifications to trigger heavy upload operations in the background. Since we suspected this behavior might be contributing to the issue, we completely stopped using this mechanism approximately two weeks ago. However, the background terminations are still occurring. We would like to better understand the possible causes of this behavior. Specifically, could this be related to: Watchdog terminations Background assertion or lifecycle violations RunningBoard resource management Jetsam policies Background execution timeouts Any other system-level resource or process management constraints We would greatly appreciate any guidance on how to identify the root cause or which logs/diagnostics we should focus on to further investigate the issue. Thank you.
2
0
220
2w
Background Location Tracking Not Reliably Relaunching App After Termination
We are developing a mileage tracking application that depends on continuous background location updates on iOS. Our app has the required background modes enabled: <key>UIBackgroundModes</key> <array> <string>remote-notification</string> <string>processing</string> <string>fetch</string> <string>location</string> </array> We are observing inconsistent behavior with background location tracking in app terminated state. In some cases, after a period of time, location updates stop completely. Sometimes iOS successfully relaunches the app when movement is detected and location updates resume correctly. However, in other cases, the app is not relaunched by the system, and we stop receiving location updates entirely. We reviewed Apple’s documentation on handling background location updates: https://developer.apple.com/documentation/corelocation/handling-location-updates-in-the-background Based on our observations, we would appreciate clarification on the following points: Is this considered expected iOS behavior or a system limitation? Under what conditions does iOS decide not to relaunch a terminated app for location events? Are there recommended best practices to improve the reliability of background location relaunch behavior? Is there any logging, diagnostics, or debugging mechanism available to determine why the app was not relaunched? Apple’s documentation mentions that location updates may be queued while the app is terminated and later delivered after relaunch. However, in some scenarios we do not receive those queued updates after the app restarts. Under what conditions can queued location updates be discarded or not delivered? Additional notes: We are using standard Core Location background updates. “Always” location permission is granted. Background App Refresh is enabled. The issue is observed intermittently across multiple iOS devices.
4
0
459
2w
Sleep onset detection on watchOS: viable non-workout paths and CMSensorRecorder behavior
I'm building a sleep tracker for couples — the headline feature is a notification to your partner the moment you fall asleep (and another when you wake up), detected on the Apple Watch from accelerometer and heart-rate data. The detection has to happen within minutes of onset for the product to make sense. My setup HKObserverQuery on heart rate with enableBackgroundDelivery(.immediate), re-registered on foreground. WKApplicationRefreshBackgroundTask rescheduled every 15 minutes. CMSensorRecorder.recordAccelerometer(forDuration: 12 * 3600) re-armed on every wake. A van Hees-style stillness classifier reading the last ~35 minutes of the buffer, with heart rate as a soft confirmer. HealthKit and Motion & Fitness authorized on both iPhone and watch. The observer's completionHandler() is called on every branch and the handler stays well under the 15-second watchdog. No HKWorkoutSession as my app is not a workout. Questions Is CMSensorRecorder paused or deprioritized while the Apple Watch's automatic sleep detection has classified the user as asleep? On a worn watch with the recorder armed for 12 hours, accelerometerData(from:to:) over a 35-minute window inside the auto-detected sleep period returns zero samples. The exact same call an hour later, once the watch has decided the user is awake, returns roughly ten thousand samples for an equivalent window. The user never activated Sleep Focus or Theater Mode — the only sleep-related state at play is the watch's own automatic detection, the same one that writes Core / REM / Deep stages into Apple Health. Is this documented power management I missed, or is it unexpected? Happy to file Feedback with a sysdiagnose during the window if you confirm it shouldn't behave this way. Is there a sanctioned non-workout path on current watchOS for detecting sleep onset within a few minutes of it happening? A full night recently produced a five-hour stretch with zero observer callbacks and zero background-refresh deliveries between bedtime and wake. The historical guidance to third-party sleep apps has been to reconstruct nights post-hoc from sleepAnalysis samples rather than attempt live detection. Is that still the recommendation today, or is there an API I've missed that would give an onset-focused app tighter wakes around bedtime? What is the current App Store review stance on HKWorkoutSession for sleep tracking? Would an app that auto-starts a .other / indoor workout only when its own classifier detects pre-sleep signals at the user's typical bedtime, ends the session as soon as onset is confirmed, never starts one outside that gated condition, and explicitly discloses "sleep tracking via workout session" in the App Store metadata — be an acceptable pattern, or grounds for rejection regardless of disclosure?
1
0
135
2w
Seeking Apple Recommended Solution for Extended, Deterministic Background Sync/Upload for Offline-First App (Large Data)
Context Our enterprise application is offline-first for iOS and iPadOS, designed to work completely offline, storing a very large local database (DB) and many attached files (images and videos) locally. Users create and update entities on the device.1 When connectivity is available, the app performs a bidirectional sync: local changes (including multi-gigabyte files) are uploaded, and thousands of DB updates are pulled down and applied locally. The Challenge: Foreground Requirement The complete sync process often requires 10 to 20 minutes to finish. Users expect their devices to proactively sync when online, even if it takes this long. Our fundamental problem is that, at present, users must keep the app in the foreground to complete the task. We have confirmed that on iOS, the system aggressively terminates the app process, typically after 30 seconds of being sent to the background. We currently advise users with large projects to keep the app in the foreground and connected to power.2 Existing Mitigation and Technical Details We have implemented several best practices to optimize transfers and manage device resources: We use battery checks before initiating large transfers, with a low battery threshold (around 15%) to pause actions if the device will enter a danger zone.2 Our upload mechanism uses HTTP Range Requests to implement a resumable single-stream approach for maximum throughput, ensuring that if a connection drops mid-transfer (even at 1.2 GB of a 2.5 GB file), we only re-transfer the remaining bytes, rather than losing all progress. This addresses network resilience and speed but not the OS background limitation.3 The Core Issue The various background options provided by iOS and iPadOS do not appear deterministic enough to reliably handle the immediate, extended data synchronization (uploading GB files and pulling down substantial DB changes) that we require. We are seeking a solution where a user-initiated task engages in background work almost immediately, reliably continuing for 10–20+ minutes after the user leaves the app or locks the screen, allowing for more "natural" device usage. Our Question for Apple Engineering Given the high volume of data transfer and the need for deterministic, extended background execution, what is Apple's current recommended, official approach for an enterprise app that requires prolonged background syncs—specifically, how can we architect this on iOS/iPadOS to reliably continue the upload and download of large data sets and database updates after the app moves out of the foreground?
2
0
125
2w
Moving to Fewer, Larger Transfers
Note Much of this content has been rolled into URL Loading System documentation, but I’m leaving this doc here for my own reference. URLSession background sessions are optimised for transferring a small number of large resources. Moreover, it’s best if the transfer is resumable. This design makes the best use of client device resources and the available network bandwidth. If your app runs a lot of tasks in a background session, you should rethink its design. Below you’ll find a number of options you might consider. Most of these options require server-side support. If your server does not have this support, and you can’t add it — perhaps you’re writing a client app for a server you don’t control — you won’t be able to implement these options directly. In that case consider creating your own server that sits between your app and the final server and implements the necessary smarts required to optimise your app’s network usage. If that’s not possible, a final option is to not use a background session but instead take advantage of the Background Tasks framework. See Background Tasks Framework, below. Basics The basic strategy here is to have the sender (the server for a download, your app for an upload) pack the data into some sort of archive, transfer that archive over the network, and then have the receiver unpack it. There are, however, a number of complications, as described in the subsequent sections. Archive Format The obvious choices for the archive format are zip and tar. macOS has lots of options for handling these formats but none of that support is present on iOS (r. 22151959). OTOH, it’s easy to find third-party libraries to fill in this gap. Incremental Transfers It’s common to have a corpus of data at one end of the connection that you need to replicate at the other. If the data is large, you don’t want to transfer the whole thing every time there’s an update. Consider using the following strategies to deal with this: Catalogue diff — In this approach the receiver first downloads a catalogue from the sender, then diffs its current state against that catalogue, then requests all the things that are missing. Alternatively, the receiver passes a catalogue of what it has to the sender, at which point the sender does the diff and returns the things that are missing. The critical part is that, once the diff has been done, all of the missing resources are transferred in a single archive. The biggest drawback here is resume. If the sender is working with lots of different receivers, each of which has their own unique needs, the sender must keep a lot of unique archives around so it can resume a failed transfer. This can be a serious headache. Versions — In this approach you manage changes to the data as separate versions. The receiver passes the version number it has to the sender, at which point the sender knows exactly what data the receiver needs. This approach requires a bit more structure but it does avoid the above-mentioned problem with resume. The sender only needs to maintain a limited number of version diffs. In fact, you can balance the number of diffs against your desire to reduce network usage: Maintaining a lot of diffs means that you only have to transfer exactly what the receiver needs, while maintaining fewer diffs makes for a simpler server at the cost of a less efficient use of the network. Download versus Upload The discussion so far has applied equally to both downloads and uploads. Historically, however, there was one key difference: URLSession did not support resumable uploads. IMPORTANT Starting with iOS 17, URLSession supports resumable uploads. See WWDC 2023 Session 10006 Build robust and resumable file transfers for the details. The rest of this section assumes that you don’t have access to that support, either because you’re working on an older system or because the server you’re uploading to doesn’t support this feature. When doing a non-resumable upload you have to balance the number of tasks you submit to the session against the negative effects of a transfer failing. For example, if you do a single large upload then it’s annoying if the transfer fails when it’s 99% complete. On the other hand, if you do lots of tiny uploads, you’re working against the URLSession background session design. It is possible to support resumable uploads with sufficient server-side support. For example, you could implement an algorithm like this: Run an initial request to allocate an upload ID. Start the upload with that upload ID. If it completes successfully, you’re done. If it fails, make a request with the upload ID to find out how much the server received. Start a new upload for the remaining data. Indeed, this is kinda how the built-in resumable upload support works. If you’re going to implement something like this, it’s best to implement that protocol. (r. 22323347) Background Tasks Framework If you’re unable to use an URLSession background session effectively, you do have an alternative, namely, combining a standard session with the Background Tasks framework. There are two options that you might find useful. The first is a processing task. This allows you to request extended background processing time from the system. Once you’ve been granted that time, use it to run your many small network requests in a standard session. The main drawback to this approach is latency: The system may not grant your request for many hours. Indeed, it’s common for these requests to run overnight, once the user has connected their device to a power source. The second is a continued processing task. This allow you to request continued execution in the background to complete a user-visible task that the user has started in the foreground. This approach has some limitations: You have to start the work when your app is in the foreground. The task is visible to the user, who can cancel it. The system may expire the task for its own reasons. Background Assets Framework If you’re using URLSession to download assets for your app or game, check out the Background Assets framework. Share and Enjoy — Quinn “The Eskimo!” @ Developer Technical Support @ Apple let myEmail = "eskimo" + "1" + "@" + "apple.com" Revision History 2026-05-27 Updated the Background Tasks Framework section to talk about continued processing task. 2023-09-27 Added information about the new resumable upload support. Added the Background Assets Framework section. Made significant editorial changes. 2022-01-31 Fixed the formatting and tags. Added a link to the official docs. 2018-03-24 Added the Background Tasks Framework section. Other editorial changes. 2015-08-18 First written.
0
0
6.2k
2w
iOS 26.5 SIGKILLs audio-recording app at ~50s of background despite UIBackgroundModes: audio - what is the supported API path?
Hi, hoping for guidance on what's a long-running bug for our app. The problem We have a transcription app on iPhone 17 Pro Max running iOS 26.5. Recording flow uses AVAudioEngine.installTap(onBus:) to capture PCM into a JS bridge for streaming to a remote transcription service. A parallel AVAudioRecorder writes the same audio to disk as backup. When the user starts a recording and locks the phone, iOS terminates our process with SIGKILL at approximately 50 seconds of continuous background time, despite: UIBackgroundModes includes audio (verified in shipping IPA's Info.plist) AVAudioSession.setCategory(.playAndRecord, mode: .default) is active AVAudioEngine is running with installTap producing PCM buffers right up to the moment of death UIApplication.backgroundTimeRemaining returns Double.greatestFiniteMagnitude at applicationDidEnterBackground (verified in our event log) No AVAudioSession.interruptionNotification is delivered before the kill. iOS terminates the process cleanly with no warning event to our observer. Evidence Our Swift observer module writes an event log to disk on every system event. On relaunch we ship it to our crash reporter. Excerpt from a recent kill on iOS 26.5 / build 2.1.32: T=0.000s session-start (engineRunning: true) T=57.199s app-will-resign-active (bufferCallbackCount: 22) T=58.913s app-did-enter-background (backgroundTimeRemaining: infinity, bufferCallbackCount: 39) [no further audio events captured] [Swift heartbeat written every 5s for next ~46 seconds] T~105s Process SIGKILLed (heartbeat last-alive: 09:31:01.597Z) Background time before kill: ~46 seconds. engineRunning: true and bufferCallbackCount was still incrementing at the moment the event log stops capturing - the audio engine was alive and feeding buffers when iOS terminated us. What we've tried (35 documented attempts) Hopefully not all relevant but listing for completeness: Various AVAudioSession category/mode/options combinations (Default, Measurement, VoiceChat, .mixWithOthers, .defaultToSpeaker, .allowBluetoothHFP) Parallel AVAudioRecorder writing a .caf file as a "real recording app" signal SFSpeechRecognizer with requiresOnDeviceRecognition = true consuming PCM in-process (50s request rotation) BGContinuedProcessingTask with Progress.completedUnitCount reporting monotonic progress every 5 seconds Live Activity (ActivityKit) with NSSupportsLiveActivitiesFrequentUpdates = true Live Activity update pushes via APNs (confirmed wake widget extension only, not host) Silent device-token APNs background pushes (confirmed iOS ~5/day rate limit) CallKit fake call (CXProvider + CXCallController) - works but creates the green pill UI which our product can't ship WebRTC peer connection with active media stream (via react-native-webrtc loopback) UIBackgroundModes: voip declaration (without CallKit) beginBackgroundTask + engine bounce (Apple's own guidance says don't, our test confirmed it's actively harmful) CLLocationManager background updates All die at ~50s background. None of them survive. What works on the same device Three App Store transcription apps survive indefinite background recording on our exact device + iOS version. We have inspected their IPAs (Mach-O LC_LOAD_DYLIB analysis + embedded entitlement extraction): Otter (com.aisense.otter) - UIBackgroundModes: audio + fetch + processing + remote-notification. Uses OneSignal-driven Live Activity push tokens + NotificationServiceExtension. No CallKit, PushKit, or WebRTC. Granola (com.granola.ios-prod) - has UIBackgroundModes: voip but the voip is for their separate outbound-phone-call feature (TwilioVoice + CallKit, lives in their PhoneCalls.framework). Recording-path uses ONLY AVAudioRecorder + PlayAndRecord + ModeDefault + Live Activity with frequentPushesEnabled. Zero PushKit anywhere in the bundle. Transcribe Speech to Text by DENIVIP (ru.denivip.transcribe) - the smallest API surface: UIBackgroundModes: audio + remote-notification only. AVAudioEngine + .playAndRecord + .default + SFSpeechRecognizer consuming PCM. No CallKit, PushKit, BGTask, Live Activity, WebRTC, or VoIP. Three apps, three different mechanisms, all working. We've implemented bits of all three approaches in our app and still die at 50s. Apple Voice Memos (system app, private entitlements) also survives indefinite recording on the same device. Questions What is the supported API path for indefinite background microphone-only recording on iOS 26.5? Voice Memos and competitor apps clearly accomplish this - what's the missing piece? Why does UIApplication.backgroundTimeRemaining return Double.greatestFiniteMagnitude at applicationDidEnterBackground but the process is terminated ~50 seconds later? Is the meaning of this property changing in iOS 26? What causes the iOS 26 process scheduler to revoke the audio-mode background runtime classification? No AVAudioSession.interruptionNotification is delivered before SIGKILL. Where can we observe the classification change? Does iOS 26 distinguish "audio recording with no audible output" from "audio recording with audible output (e.g. a media playback session)"? If so, what is the supported API to register as a recording-only background-audio app? Does BGContinuedProcessingTask (new in iOS 26) actually extend background CPU time for an app that is also using UIBackgroundModes: audio and an active AVAudioSession? Or is it for finish-what-you-started bursts only (per WWDC 2025 session 227)? Any guidance - even pointers to specific WWDC sessions, sample code, or technotes - would be hugely appreciated. We've spent ~40+ hours on this and want to know what the supported path looks like in iOS 26. Happy to share more event-log data, IPA inspection notes, or build a focused Xcode reproduction if helpful. Thanks!
1
0
329
3w
SwiftData with CloudKit Error: Error updating background task request
Hi, Overview I have a SwiftData project which automatically syncs with CloudKit. When I run the app, I see the following error in Xcode logs. Error updating background task request: Error Domain=BGSystemTaskSchedulerErrorDomain Code=3 "(null)" My attempt I can enable Background processing (under Signing & Capabilities > Background modes), but I don't know the BGTaskSchedulerPermittedIdentifiers to add in the Info.plist Questions How can I resolve this? If I should enable background processing, what are the BGTaskSchedulerPermittedIdentifiers to add in Info.plist?
18
0
1.2k
3w
iOS feasibility question: user-initiated wake-word detection during active session
Hi all, Technical architecture question for those experienced with iOS background audio / microphone constraints. I’m exploring an app concept where: the user explicitly starts a temporary active session during that session, on-device wake-word / keyword detection runs locally no audio is stored or transmitted during passive monitoring monitoring stops when the user ends the session The intended UX is that the user may then lock the phone or place it away while the active session remains in progress. Question: Is there any App Store-compliant architecture that would allow local keyword / wake-word detection to continue while the device is locked or the app is backgrounded during that active session? Or would iOS lifecycle / background execution rules make this infeasible for custom wake-word detection? Interested in practical experience around: AVAudioSession background audio modes on-device speech processing App Review acceptability Thanks in advance.
0
0
438
4w
HealthKit Background Sync: How Close to Real-Time Can We Reliably Get?
I am building an iOS mobile application using Flutter, with native Swift integration for accessing Apple HealthKit instead of a Flutter plugin. The primary goal is to capture and sync specific HealthKit data types, namely Respiratory Rate and Sleeping Wrist Temperature, and send this data to a backend API as close to real-time as possible after it is written to HealthKit. The application needs to support both foreground and background syncing. Data should be synced when the app is opened, but also in the background when the device is locked. Additionally, there are reliability constraints to consider: the user may not open the app for extended periods, the device may remain locked, and Low Power Mode or other system restrictions may impact background execution. I have explored a few possible approaches. One option is using BGTaskScheduler to periodically fetch and sync data. However, based on my understanding, background tasks are not guaranteed to execute frequently and may be throttled or stopped by the system after some time. Another approach is to use HKObserverQuery along with HKAnchoredObjectQuery. In this setup, observer queries would be registered for the required data types, background delivery would be enabled, and whenever triggered, anchored queries would fetch incremental updates which would then be sent to the backend. This seems closer to a real-time model, but I am unsure how reliable and timely these background updates are in practice. I have also looked into newer APIs like HKQueryDescriptor, but it is not clear whether they provide any advantage over the observer plus anchored query approach for this use case. My main questions are: what is the recommended architecture for achieving near real-time syncing of HealthKit data for these metrics? Does HealthKit background delivery provide any guarantees or expectations around delivery timing, or can updates be significantly delayed depending on system conditions? How should edge cases be handled, such as when the device remains locked for long durations or when Low Power Mode is enabled? Would it be advisable to combine observer queries with BGTaskScheduler as a fallback mechanism? Finally, apps like Athlytic appear to show updated data immediately when opened. I am curious whether this is primarily achieved through background delivery or by fetching data on demand when the app becomes active. The goal is to design a system that is as close to real-time as possible while remaining reliable and compliant with iOS background execution constraints. Any recommended patterns, best practices, or references would be greatly appreciated.
1
0
364
May ’26
applicationWillTerminate to wrap up Background Recording
Hello together, the user is able to do recordings with my app. The recordings also runs, while the App is in Background. I have Background Modes Audio & Background enabled. When the user accidentally terminates the App while the recording is still running, the whole recording is lost. I tried AppDelegate applicationWillTerminate on my iOS 26 App and it works perfectly to wrap up the LiveActivity that is shown while the recording is active. But it does not save the Audio and also doesn't update the Widgets (they are interactive and show a different state while recording and stay stuck in recording-state on accidental termination). Any ideas? Best wishes, Dominik
2
0
368
May ’26
Recommended Architecture for Near-Real-Time Local Device Monitoring in Background
Hello, We are designing an iOS application for a vehicle safety use case. The app connects to a local network device (a DVR installed in the vehicle) and processes image frames to detect passenger-left-behind items, then alerts the driver if needed. We would like to better understand the recommended and App Store-compliant architecture for handling this scenario, especially when the app is not in the foreground. Current Requirements The app communicates with a local network device over Wi-Fi The device can provide image data The app performs or triggers AI inference based on the received data When a relevant event is detected, the app needs to notify the user (e.g., audio alert) Questions Background Execution Model For a near-real-time monitoring scenario, what architectural patterns are recommended on iOS when the app is running in the background? Background Modes Consideration In this type of use case, are any existing background modes (such as location or external accessory) considered appropriate when used strictly within their intended purpose? Enterprise / Managed Deployment Are there any specific entitlements or capabilities available in enterprise or commercial deployments that may allow more persistent local network communication under certain conditions?
1
0
169
Apr ’26
Safari web extensions: Optimal IPC architecture between extension and the containing app
I'm building a macOS safari extension and porting its functionality from a chrome extension. The chrome extension uses native messaging hosts to communicate with another process using IPC and holding a persistent connection. To use the same functionality in Safari, I understand that will need to use the handler to communicate it to the containing app, and the app will have to hold the persistent IPC connection. My question derives from that concept: should the app be running in a long-lived state? And if so, how can I ensure that app be running 100% of the time. Also is there any way I can control it's lifecycle with the Safari browser's lifecycle? I will not be using XPC here, but a different UDS to make the connection. Also in addition to that, what would you recommend the best approach is the communicate between the extension and it's handler? -> should it be again a UDS or userDefaults +darwin notification be enough? Also I wouldn't want the inter-message relayed between components to be dropped, is there a fault tolerant architecture you would recommend?
0
0
330
Apr ’26
Background Tasks Resources
General: Forums subtopic: App & System Services > Processes & Concurrency Forums tag: Background Tasks Background Tasks framework documentation UIApplication background tasks documentation ProcessInfo expiring activity documentation Using background tasks documentation for watchOS Performing long-running tasks on iOS and iPadOS documentation WWDC 2020 Session 10063 Background execution demystified — This is critical resource. Watch it! [1] WWDC 2022 Session 10142 Efficiency awaits: Background tasks in SwiftUI WWDC 2025 Session 227 Finish tasks in the background — This contains an excellent summary of the expected use cases for each of the background task types. iOS Background Execution Limits forums post UIApplication Background Task Notes forums post Testing and Debugging Code Running in the Background forums post Share and Enjoy — Quinn “The Eskimo!” @ Developer Technical Support @ Apple let myEmail = "eskimo" + "1" + "@" + "apple.com" [1] Sadly the video is currently not available from Apple. I’ve left the link in place just in case it comes back.
Replies
0
Boosts
0
Views
4.5k
Activity
Nov ’25
Maximum number of BGContinuedProcessingTasks?
I have a weird situation arising in my app where calling BGTaskScheduler.shared.submit(request) seems to fail silently, without raising any of the BGTaskScheduler.Error's. Here's what's happening. A user registers and submits 5 BGContinuedProcessingTask's, with different ID's using the wildcard. When trying to submit the 6th task like this: try bgTask.submit() //submit task isCreatingBGTask = false // toggle ProgressView off dismiss() //Dismiss the sheet The sheet will dismiss, but the device never gives the haptic feedback, and the task is not visible in the notification centre. Having a maximum number of running tasks makes sense, but why isn't it raising the error BGTaskScheduler.Error(.immediateRunIneligible). It also doesn't seem like there's a way to query the tasks that are in progress (at least I couldn't find a way). So for now I'll just track my own tasks manually, and prevent submission at 5 tasks, but I'm wondering what would happen if another app had 2 tasks going, and then my user tries to submit 3 or something like that.
Replies
0
Boosts
0
Views
16
Activity
10h
PHAssetResourceUploadJobChangeRequest doesn't upload iCloud-optimized photos — is this expected?
I'm implementing PHBackgroundResourceUploadExtension to back up photos and videos to our cloud storage service. During testing, I observed that iCloud-optimized photos (where the full-resolution original is stored in iCloud, not on device) do not upload. The upload job appears to silently skip these assets. Questions: Is this behavior intentional/documented? I couldn't find explicit mention of this limitation. If the device only has the optimized/thumbnail version locally, does the system: - Automatically download the full-resolution asset from iCloud before uploading? - Skip the asset entirely? - Return an error via PHAssetResourceUploadJobChangeRequest? For a complete backup solution, should we: - Pre-fetch full-resolution assets using PHAssetResourceManager.requestData(for:options:) before creating upload jobs? - Use a hybrid approach (this extension for local assets + separate logic for iCloud-only assets)? Environment: iOS 26, Xcode 18
Replies
1
Boosts
1
Views
247
Activity
2d
How to upload large videos with PHAssetResourceUploadJobChangeRequest?
I'm implementing a PHBackgroundResourceUploadExtension to back up photos and videos from the user's library to our cloud storage service. Our existing upload infrastructure uses chunked uploads for large files (splitting videos into smaller byte ranges and uploading each chunk separately). This approach: Allows resumable uploads if interrupted Stays within server-side request size limits Provides granular progress tracking Looking at the PHAssetResourceUploadJobChangeRequest.createJob(destination:resource:) API, I don't see a way to specify byte ranges or create multiple jobs for chunks of the same resource. Questions: Does the system handle large files (1GB+) automatically under the hood, or is there a recommended maximum file size for a single upload job? Is there a supported pattern for chunked/resumable uploads, or should the destination URL endpoint handle the entire file in one request? If our server requires chunked uploads (e.g., BITS protocol with CreateSession → Fragment → CloseSession), is this extension the right mechanism, or should we use a different approach for large videos? Any guidance on best practices for large asset uploads would be greatly appreciated. Environment: iOS 26, Xcode 18
Replies
5
Boosts
1
Views
911
Activity
2d
How to reliably debug PHBackgroundResourceUploadExtension during development?
I'm developing a PHBackgroundResourceUploadExtension and finding it difficult to debug because the system controls when the extension launches. Current experience: The extension starts at unpredictable times (anywhere from 1 minute to several hours after photos are added) By the time I attach the debugger, the upload may have already completed or failed Breakpoints in init() or early lifecycle methods are often missed Questions: Is there a way to force-launch the extension during development (similar to how we can manually trigger Background App Refresh in Xcode)? Are there any launch arguments or environment variables that put the extension in a debug/eager mode? I tried taking photos/videos, but this doesn't trigged app extension in all cases. Any tips for improving the debug cycle would be greatly appreciated. Environment: iOS 26, Xcode 18
Replies
2
Boosts
1
Views
707
Activity
3d
Network Socket Background Task
Hello everyone, I have developed an app that is a local networking monitor app for a specific building automation protocol. I have searched the forum and I think I have found some older posts regarding this topic but I could not figure out if my issue falls under the same category. So my app allows the user to connect to local protocol devices, and start a monitor session where they can see incoming/outgoing packets. The connections are UDP or TCP and require opening a socket. Currently, backgrounding the app will make the OS terminate the socket connection, therefore ending the monitor, even if the app is backgrounded by user, to let's say, perform some other task in their phone. I have several requests from users to improve the app by allowing the monitor to continue while the app is backgrounded. However, by reading the relevant documents, I have found this to be almost impossible in iOS app. I have considered: Remote Push Notifications (APNs): The app operates on LAN so this is not an option, since I do not have an infrastructure to somehow send notifications to keep app process alive. Background Tasks (BGTaskScheduler): Not my case, since I do not want periodic execution. The app requires continuous socket listening. VoIP, VPN, or Audio Background Modes: My app does not fall under any of these categories, even though this would solve my situation. By searching around a bit more, I might be able to use either BGProcessingTask, which would allow my app at least to run for some minutes and show the user that they have to foreground it in order to not stop the monitor process, or maybe even App Intents framework. Has anyone faced similar requirement for their app? Any tip or point to a direction I should investigate more? Thanks, Nikos
Replies
0
Boosts
0
Views
27
Activity
3d
Is the Dock "Running in Background" indicator supposed to trigger for registered launchd jobs with no live process on macOS 27?
I just noticed something on macOS 27 beta 1 and I'm not sure if it's a bug or just how the new feature works. After quitting an app with Cmd+Q, the Dock keeps showing the gray dot with the "Running in Background" message. So I checked — ps aux shows nothing running for the app at all. The only trace is its auto-updater job in launchctl list (com.anthropic.claudefordesktop.ShipIt), which is registered but has no PID, so it's not actually executing anything. Out of curiosity I tried Discord and got the exact same thing (com.discord.discord.ShipIt), so this probably happens with any Electron app that uses the Squirrel updater. Is this intended behavior? Trying to understand if the indicator reflects registered background items (and not just live processes) so I know what to expect for Electron-based apps.
Replies
0
Boosts
0
Views
49
Activity
4d
Reliable network request from a terminated, PushKit-launched app during CXEndCallAction
Environment: iOS 18.7.8, CallKit + PushKit VoIP. On VoIP push we call reportNewIncomingCall and show the system CallKit UI. Goal: When the user declines from the CallKit UI, send a single HTTPS POST to our backend in realtime, across all app states. Problem: Foreground and backgrounded states work. When the app is terminated (system-evicted or user-force-quit), the push launches the app, CallKit shows, and we receive CXEndCallAction — but the network request doesn't reliably leave the device. The process is suspended/terminated moments after the action returns. Tried: URLSession.shared dataTask inside CXEndCallAction — frozen with the app; resumes only on next foreground launch. beginBackgroundTask(withName:) around the request — insufficient when terminated. Background URLSession (.background, isDiscretionary = false, sessionSendsLaunchEvents = true, uploadTask(fromFile:), body staged in Caches, held briefly with a task assertion). Reliable when backgrounded; still unreliable/delayed when terminated, especially after force-quit. Questions: Is reliable, near-realtime client network delivery from a terminated, PushKit-launched app possible, or is this an inherent platform constraint? If it's a constraint, is the recommended pattern to treat the decline as best-effort and make the server authoritative (e.g., ring timeout)? Any official references? Does force-quit vs. system termination change background-execution / background-URLSession guarantees, and is there a supported approach for force-quit specifically? Any API we missed (e.g., a sanctioned way to extend runtime during CXEndCallAction, or background-URLSession scheduling guarantees for VoIP) that makes this realtime-reliable?
Replies
0
Boosts
0
Views
38
Activity
6d
Background Assets: Downloaded .aar not working — "bundle record couldn't be looked up" error (-10814)
Platform: iOS 26 (23E254) Xcode: 26.0 Reproduces on: Debug builds AND TestFlight Summary: I'm using Apple-Hosted Managed Background Assets with on-demand download policy. The .aar archives download successfully (correct file size, status = downloaded), but the contents are never extracted into the asset pack namespace. AssetPackManager.shared.contents(at:) returns fileNotFound for all path variants, and url(for: FilePath(".")) returns a URL that exists but contains zero children. Root Cause from Sysdiagnose: The backgroundassets.user daemon logs reveal this error on every download attempt: A bundle record couldn't be looked up for the application identifier "AtlasDrift.SnapTrail": Error Domain=NSOSStatusErrorDomain Code=-10814 "(null)" UserInfo={_LSFile=LSBindingEvaluator.mm, _LSLine=1973, _LSFunction=runEvaluator} Error code -10814 is kLSApplicationNotFoundErr. The BA daemon downloads the .aar blob, then attempts to find the app bundle via LaunchServices to locate the extension for extraction — but the LS lookup fails. Without the extension, extraction never occurs. Verified Configuration Everything matches the documentation and WWDC sessions: Extension embedded at SnapTrail.app/Extensions/BackgroundDownloadExtension.appex Bundle IDs: App = AtlasDrift.SnapTrail, Extension = AtlasDrift.SnapTrail.BackgroundDownloadExtension (correct parent-child pattern) Extension point: com.apple.background-asset-downloader-extension Product type: com.apple.product-type.extensionkit-extension Protocol: StoreDownloaderExtension from StoreKit (for Apple-hosted packs) App group: group.AtlasDrift.SnapTrail (matching in both app and extension entitlements) Info.plist keys: BAAppGroupID, BAHasManagedAssetPacks = YES BAUsesAppleHosting = YES (no BAInitialDownloadRestrictions or other BA keys) .aar Packaging Archives built with xcrun ba-package from the Assets directory. Manifest format: { "assetPackID": "ireland", "downloadPolicy": { "onDemand": {} }, "fileSelectors": [{ "directory": "POIRegions/ireland/IR" }], "platforms": ["iOS"] } Uploaded via App Store Connect API with assetType: "ASSET". Diagnostic Observations AssetPackManager.shared.assetPack(withID:) returns valid metadata (correct download size) ensureLocalAvailability(of:) completes without error assetPackIsAvailableLocally(withID:) returns true url(for: FilePath(".")) returns a URL that exists but has zero children (empty namespace) contents(at:) returns fileNotFound for all path variants tested The extension never runs — breadcrumb file written in init() is never created The -10814 error appears in daemon logs for every download cycle Questions Has anyone successfully used Apple-Hosted Managed Background Assets on iOS 26 beta? Is the daemon's LaunchServices integration known to be broken in this seed? Is there anything about the bundle identifier format or provisioning profile setup that could cause the BA daemon's LS lookup to fail, even though the app installs and runs fine otherwise? Are there any additional Info.plist keys or entitlements beyond what's documented that might be required for the daemon to locate the app bundle? Any guidance would be appreciated. I've filed a Feedback report with the full sysdiagnose attached.
Replies
2
Boosts
0
Views
426
Activity
1w
Background Termination Investigation
Hello, We are currently investigating an issue where our app is being terminated by the system while running in the background. At the moment, the app does not perform any significant background activity, and memory usage remains relatively low (approximately 150–200 MB). Despite this, the app is still being terminated in the background, even under conditions where other apps appear to remain active. From our investigation so far, the issue does not appear to be related to: High memory consumption Explicit background task misuse Application crashes on our side For additional context, we had previously used silent push notifications to trigger heavy upload operations in the background. Since we suspected this behavior might be contributing to the issue, we completely stopped using this mechanism approximately two weeks ago. However, the background terminations are still occurring. We would like to better understand the possible causes of this behavior. Specifically, could this be related to: Watchdog terminations Background assertion or lifecycle violations RunningBoard resource management Jetsam policies Background execution timeouts Any other system-level resource or process management constraints We would greatly appreciate any guidance on how to identify the root cause or which logs/diagnostics we should focus on to further investigate the issue. Thank you.
Replies
2
Boosts
0
Views
220
Activity
2w
Background Location Tracking Not Reliably Relaunching App After Termination
We are developing a mileage tracking application that depends on continuous background location updates on iOS. Our app has the required background modes enabled: <key>UIBackgroundModes</key> <array> <string>remote-notification</string> <string>processing</string> <string>fetch</string> <string>location</string> </array> We are observing inconsistent behavior with background location tracking in app terminated state. In some cases, after a period of time, location updates stop completely. Sometimes iOS successfully relaunches the app when movement is detected and location updates resume correctly. However, in other cases, the app is not relaunched by the system, and we stop receiving location updates entirely. We reviewed Apple’s documentation on handling background location updates: https://developer.apple.com/documentation/corelocation/handling-location-updates-in-the-background Based on our observations, we would appreciate clarification on the following points: Is this considered expected iOS behavior or a system limitation? Under what conditions does iOS decide not to relaunch a terminated app for location events? Are there recommended best practices to improve the reliability of background location relaunch behavior? Is there any logging, diagnostics, or debugging mechanism available to determine why the app was not relaunched? Apple’s documentation mentions that location updates may be queued while the app is terminated and later delivered after relaunch. However, in some scenarios we do not receive those queued updates after the app restarts. Under what conditions can queued location updates be discarded or not delivered? Additional notes: We are using standard Core Location background updates. “Always” location permission is granted. Background App Refresh is enabled. The issue is observed intermittently across multiple iOS devices.
Replies
4
Boosts
0
Views
459
Activity
2w
Sleep onset detection on watchOS: viable non-workout paths and CMSensorRecorder behavior
I'm building a sleep tracker for couples — the headline feature is a notification to your partner the moment you fall asleep (and another when you wake up), detected on the Apple Watch from accelerometer and heart-rate data. The detection has to happen within minutes of onset for the product to make sense. My setup HKObserverQuery on heart rate with enableBackgroundDelivery(.immediate), re-registered on foreground. WKApplicationRefreshBackgroundTask rescheduled every 15 minutes. CMSensorRecorder.recordAccelerometer(forDuration: 12 * 3600) re-armed on every wake. A van Hees-style stillness classifier reading the last ~35 minutes of the buffer, with heart rate as a soft confirmer. HealthKit and Motion & Fitness authorized on both iPhone and watch. The observer's completionHandler() is called on every branch and the handler stays well under the 15-second watchdog. No HKWorkoutSession as my app is not a workout. Questions Is CMSensorRecorder paused or deprioritized while the Apple Watch's automatic sleep detection has classified the user as asleep? On a worn watch with the recorder armed for 12 hours, accelerometerData(from:to:) over a 35-minute window inside the auto-detected sleep period returns zero samples. The exact same call an hour later, once the watch has decided the user is awake, returns roughly ten thousand samples for an equivalent window. The user never activated Sleep Focus or Theater Mode — the only sleep-related state at play is the watch's own automatic detection, the same one that writes Core / REM / Deep stages into Apple Health. Is this documented power management I missed, or is it unexpected? Happy to file Feedback with a sysdiagnose during the window if you confirm it shouldn't behave this way. Is there a sanctioned non-workout path on current watchOS for detecting sleep onset within a few minutes of it happening? A full night recently produced a five-hour stretch with zero observer callbacks and zero background-refresh deliveries between bedtime and wake. The historical guidance to third-party sleep apps has been to reconstruct nights post-hoc from sleepAnalysis samples rather than attempt live detection. Is that still the recommendation today, or is there an API I've missed that would give an onset-focused app tighter wakes around bedtime? What is the current App Store review stance on HKWorkoutSession for sleep tracking? Would an app that auto-starts a .other / indoor workout only when its own classifier detects pre-sleep signals at the user's typical bedtime, ends the session as soon as onset is confirmed, never starts one outside that gated condition, and explicitly discloses "sleep tracking via workout session" in the App Store metadata — be an acceptable pattern, or grounds for rejection regardless of disclosure?
Replies
1
Boosts
0
Views
135
Activity
2w
Seeking Apple Recommended Solution for Extended, Deterministic Background Sync/Upload for Offline-First App (Large Data)
Context Our enterprise application is offline-first for iOS and iPadOS, designed to work completely offline, storing a very large local database (DB) and many attached files (images and videos) locally. Users create and update entities on the device.1 When connectivity is available, the app performs a bidirectional sync: local changes (including multi-gigabyte files) are uploaded, and thousands of DB updates are pulled down and applied locally. The Challenge: Foreground Requirement The complete sync process often requires 10 to 20 minutes to finish. Users expect their devices to proactively sync when online, even if it takes this long. Our fundamental problem is that, at present, users must keep the app in the foreground to complete the task. We have confirmed that on iOS, the system aggressively terminates the app process, typically after 30 seconds of being sent to the background. We currently advise users with large projects to keep the app in the foreground and connected to power.2 Existing Mitigation and Technical Details We have implemented several best practices to optimize transfers and manage device resources: We use battery checks before initiating large transfers, with a low battery threshold (around 15%) to pause actions if the device will enter a danger zone.2 Our upload mechanism uses HTTP Range Requests to implement a resumable single-stream approach for maximum throughput, ensuring that if a connection drops mid-transfer (even at 1.2 GB of a 2.5 GB file), we only re-transfer the remaining bytes, rather than losing all progress. This addresses network resilience and speed but not the OS background limitation.3 The Core Issue The various background options provided by iOS and iPadOS do not appear deterministic enough to reliably handle the immediate, extended data synchronization (uploading GB files and pulling down substantial DB changes) that we require. We are seeking a solution where a user-initiated task engages in background work almost immediately, reliably continuing for 10–20+ minutes after the user leaves the app or locks the screen, allowing for more "natural" device usage. Our Question for Apple Engineering Given the high volume of data transfer and the need for deterministic, extended background execution, what is Apple's current recommended, official approach for an enterprise app that requires prolonged background syncs—specifically, how can we architect this on iOS/iPadOS to reliably continue the upload and download of large data sets and database updates after the app moves out of the foreground?
Replies
2
Boosts
0
Views
125
Activity
2w
Moving to Fewer, Larger Transfers
Note Much of this content has been rolled into URL Loading System documentation, but I’m leaving this doc here for my own reference. URLSession background sessions are optimised for transferring a small number of large resources. Moreover, it’s best if the transfer is resumable. This design makes the best use of client device resources and the available network bandwidth. If your app runs a lot of tasks in a background session, you should rethink its design. Below you’ll find a number of options you might consider. Most of these options require server-side support. If your server does not have this support, and you can’t add it — perhaps you’re writing a client app for a server you don’t control — you won’t be able to implement these options directly. In that case consider creating your own server that sits between your app and the final server and implements the necessary smarts required to optimise your app’s network usage. If that’s not possible, a final option is to not use a background session but instead take advantage of the Background Tasks framework. See Background Tasks Framework, below. Basics The basic strategy here is to have the sender (the server for a download, your app for an upload) pack the data into some sort of archive, transfer that archive over the network, and then have the receiver unpack it. There are, however, a number of complications, as described in the subsequent sections. Archive Format The obvious choices for the archive format are zip and tar. macOS has lots of options for handling these formats but none of that support is present on iOS (r. 22151959). OTOH, it’s easy to find third-party libraries to fill in this gap. Incremental Transfers It’s common to have a corpus of data at one end of the connection that you need to replicate at the other. If the data is large, you don’t want to transfer the whole thing every time there’s an update. Consider using the following strategies to deal with this: Catalogue diff — In this approach the receiver first downloads a catalogue from the sender, then diffs its current state against that catalogue, then requests all the things that are missing. Alternatively, the receiver passes a catalogue of what it has to the sender, at which point the sender does the diff and returns the things that are missing. The critical part is that, once the diff has been done, all of the missing resources are transferred in a single archive. The biggest drawback here is resume. If the sender is working with lots of different receivers, each of which has their own unique needs, the sender must keep a lot of unique archives around so it can resume a failed transfer. This can be a serious headache. Versions — In this approach you manage changes to the data as separate versions. The receiver passes the version number it has to the sender, at which point the sender knows exactly what data the receiver needs. This approach requires a bit more structure but it does avoid the above-mentioned problem with resume. The sender only needs to maintain a limited number of version diffs. In fact, you can balance the number of diffs against your desire to reduce network usage: Maintaining a lot of diffs means that you only have to transfer exactly what the receiver needs, while maintaining fewer diffs makes for a simpler server at the cost of a less efficient use of the network. Download versus Upload The discussion so far has applied equally to both downloads and uploads. Historically, however, there was one key difference: URLSession did not support resumable uploads. IMPORTANT Starting with iOS 17, URLSession supports resumable uploads. See WWDC 2023 Session 10006 Build robust and resumable file transfers for the details. The rest of this section assumes that you don’t have access to that support, either because you’re working on an older system or because the server you’re uploading to doesn’t support this feature. When doing a non-resumable upload you have to balance the number of tasks you submit to the session against the negative effects of a transfer failing. For example, if you do a single large upload then it’s annoying if the transfer fails when it’s 99% complete. On the other hand, if you do lots of tiny uploads, you’re working against the URLSession background session design. It is possible to support resumable uploads with sufficient server-side support. For example, you could implement an algorithm like this: Run an initial request to allocate an upload ID. Start the upload with that upload ID. If it completes successfully, you’re done. If it fails, make a request with the upload ID to find out how much the server received. Start a new upload for the remaining data. Indeed, this is kinda how the built-in resumable upload support works. If you’re going to implement something like this, it’s best to implement that protocol. (r. 22323347) Background Tasks Framework If you’re unable to use an URLSession background session effectively, you do have an alternative, namely, combining a standard session with the Background Tasks framework. There are two options that you might find useful. The first is a processing task. This allows you to request extended background processing time from the system. Once you’ve been granted that time, use it to run your many small network requests in a standard session. The main drawback to this approach is latency: The system may not grant your request for many hours. Indeed, it’s common for these requests to run overnight, once the user has connected their device to a power source. The second is a continued processing task. This allow you to request continued execution in the background to complete a user-visible task that the user has started in the foreground. This approach has some limitations: You have to start the work when your app is in the foreground. The task is visible to the user, who can cancel it. The system may expire the task for its own reasons. Background Assets Framework If you’re using URLSession to download assets for your app or game, check out the Background Assets framework. Share and Enjoy — Quinn “The Eskimo!” @ Developer Technical Support @ Apple let myEmail = "eskimo" + "1" + "@" + "apple.com" Revision History 2026-05-27 Updated the Background Tasks Framework section to talk about continued processing task. 2023-09-27 Added information about the new resumable upload support. Added the Background Assets Framework section. Made significant editorial changes. 2022-01-31 Fixed the formatting and tags. Added a link to the official docs. 2018-03-24 Added the Background Tasks Framework section. Other editorial changes. 2015-08-18 First written.
Replies
0
Boosts
0
Views
6.2k
Activity
2w
iOS 26.5 SIGKILLs audio-recording app at ~50s of background despite UIBackgroundModes: audio - what is the supported API path?
Hi, hoping for guidance on what's a long-running bug for our app. The problem We have a transcription app on iPhone 17 Pro Max running iOS 26.5. Recording flow uses AVAudioEngine.installTap(onBus:) to capture PCM into a JS bridge for streaming to a remote transcription service. A parallel AVAudioRecorder writes the same audio to disk as backup. When the user starts a recording and locks the phone, iOS terminates our process with SIGKILL at approximately 50 seconds of continuous background time, despite: UIBackgroundModes includes audio (verified in shipping IPA's Info.plist) AVAudioSession.setCategory(.playAndRecord, mode: .default) is active AVAudioEngine is running with installTap producing PCM buffers right up to the moment of death UIApplication.backgroundTimeRemaining returns Double.greatestFiniteMagnitude at applicationDidEnterBackground (verified in our event log) No AVAudioSession.interruptionNotification is delivered before the kill. iOS terminates the process cleanly with no warning event to our observer. Evidence Our Swift observer module writes an event log to disk on every system event. On relaunch we ship it to our crash reporter. Excerpt from a recent kill on iOS 26.5 / build 2.1.32: T=0.000s session-start (engineRunning: true) T=57.199s app-will-resign-active (bufferCallbackCount: 22) T=58.913s app-did-enter-background (backgroundTimeRemaining: infinity, bufferCallbackCount: 39) [no further audio events captured] [Swift heartbeat written every 5s for next ~46 seconds] T~105s Process SIGKILLed (heartbeat last-alive: 09:31:01.597Z) Background time before kill: ~46 seconds. engineRunning: true and bufferCallbackCount was still incrementing at the moment the event log stops capturing - the audio engine was alive and feeding buffers when iOS terminated us. What we've tried (35 documented attempts) Hopefully not all relevant but listing for completeness: Various AVAudioSession category/mode/options combinations (Default, Measurement, VoiceChat, .mixWithOthers, .defaultToSpeaker, .allowBluetoothHFP) Parallel AVAudioRecorder writing a .caf file as a "real recording app" signal SFSpeechRecognizer with requiresOnDeviceRecognition = true consuming PCM in-process (50s request rotation) BGContinuedProcessingTask with Progress.completedUnitCount reporting monotonic progress every 5 seconds Live Activity (ActivityKit) with NSSupportsLiveActivitiesFrequentUpdates = true Live Activity update pushes via APNs (confirmed wake widget extension only, not host) Silent device-token APNs background pushes (confirmed iOS ~5/day rate limit) CallKit fake call (CXProvider + CXCallController) - works but creates the green pill UI which our product can't ship WebRTC peer connection with active media stream (via react-native-webrtc loopback) UIBackgroundModes: voip declaration (without CallKit) beginBackgroundTask + engine bounce (Apple's own guidance says don't, our test confirmed it's actively harmful) CLLocationManager background updates All die at ~50s background. None of them survive. What works on the same device Three App Store transcription apps survive indefinite background recording on our exact device + iOS version. We have inspected their IPAs (Mach-O LC_LOAD_DYLIB analysis + embedded entitlement extraction): Otter (com.aisense.otter) - UIBackgroundModes: audio + fetch + processing + remote-notification. Uses OneSignal-driven Live Activity push tokens + NotificationServiceExtension. No CallKit, PushKit, or WebRTC. Granola (com.granola.ios-prod) - has UIBackgroundModes: voip but the voip is for their separate outbound-phone-call feature (TwilioVoice + CallKit, lives in their PhoneCalls.framework). Recording-path uses ONLY AVAudioRecorder + PlayAndRecord + ModeDefault + Live Activity with frequentPushesEnabled. Zero PushKit anywhere in the bundle. Transcribe Speech to Text by DENIVIP (ru.denivip.transcribe) - the smallest API surface: UIBackgroundModes: audio + remote-notification only. AVAudioEngine + .playAndRecord + .default + SFSpeechRecognizer consuming PCM. No CallKit, PushKit, BGTask, Live Activity, WebRTC, or VoIP. Three apps, three different mechanisms, all working. We've implemented bits of all three approaches in our app and still die at 50s. Apple Voice Memos (system app, private entitlements) also survives indefinite recording on the same device. Questions What is the supported API path for indefinite background microphone-only recording on iOS 26.5? Voice Memos and competitor apps clearly accomplish this - what's the missing piece? Why does UIApplication.backgroundTimeRemaining return Double.greatestFiniteMagnitude at applicationDidEnterBackground but the process is terminated ~50 seconds later? Is the meaning of this property changing in iOS 26? What causes the iOS 26 process scheduler to revoke the audio-mode background runtime classification? No AVAudioSession.interruptionNotification is delivered before SIGKILL. Where can we observe the classification change? Does iOS 26 distinguish "audio recording with no audible output" from "audio recording with audible output (e.g. a media playback session)"? If so, what is the supported API to register as a recording-only background-audio app? Does BGContinuedProcessingTask (new in iOS 26) actually extend background CPU time for an app that is also using UIBackgroundModes: audio and an active AVAudioSession? Or is it for finish-what-you-started bursts only (per WWDC 2025 session 227)? Any guidance - even pointers to specific WWDC sessions, sample code, or technotes - would be hugely appreciated. We've spent ~40+ hours on this and want to know what the supported path looks like in iOS 26. Happy to share more event-log data, IPA inspection notes, or build a focused Xcode reproduction if helpful. Thanks!
Replies
1
Boosts
0
Views
329
Activity
3w
SwiftData with CloudKit Error: Error updating background task request
Hi, Overview I have a SwiftData project which automatically syncs with CloudKit. When I run the app, I see the following error in Xcode logs. Error updating background task request: Error Domain=BGSystemTaskSchedulerErrorDomain Code=3 "(null)" My attempt I can enable Background processing (under Signing & Capabilities > Background modes), but I don't know the BGTaskSchedulerPermittedIdentifiers to add in the Info.plist Questions How can I resolve this? If I should enable background processing, what are the BGTaskSchedulerPermittedIdentifiers to add in Info.plist?
Replies
18
Boosts
0
Views
1.2k
Activity
3w
iOS feasibility question: user-initiated wake-word detection during active session
Hi all, Technical architecture question for those experienced with iOS background audio / microphone constraints. I’m exploring an app concept where: the user explicitly starts a temporary active session during that session, on-device wake-word / keyword detection runs locally no audio is stored or transmitted during passive monitoring monitoring stops when the user ends the session The intended UX is that the user may then lock the phone or place it away while the active session remains in progress. Question: Is there any App Store-compliant architecture that would allow local keyword / wake-word detection to continue while the device is locked or the app is backgrounded during that active session? Or would iOS lifecycle / background execution rules make this infeasible for custom wake-word detection? Interested in practical experience around: AVAudioSession background audio modes on-device speech processing App Review acceptability Thanks in advance.
Replies
0
Boosts
0
Views
438
Activity
4w
HealthKit Background Sync: How Close to Real-Time Can We Reliably Get?
I am building an iOS mobile application using Flutter, with native Swift integration for accessing Apple HealthKit instead of a Flutter plugin. The primary goal is to capture and sync specific HealthKit data types, namely Respiratory Rate and Sleeping Wrist Temperature, and send this data to a backend API as close to real-time as possible after it is written to HealthKit. The application needs to support both foreground and background syncing. Data should be synced when the app is opened, but also in the background when the device is locked. Additionally, there are reliability constraints to consider: the user may not open the app for extended periods, the device may remain locked, and Low Power Mode or other system restrictions may impact background execution. I have explored a few possible approaches. One option is using BGTaskScheduler to periodically fetch and sync data. However, based on my understanding, background tasks are not guaranteed to execute frequently and may be throttled or stopped by the system after some time. Another approach is to use HKObserverQuery along with HKAnchoredObjectQuery. In this setup, observer queries would be registered for the required data types, background delivery would be enabled, and whenever triggered, anchored queries would fetch incremental updates which would then be sent to the backend. This seems closer to a real-time model, but I am unsure how reliable and timely these background updates are in practice. I have also looked into newer APIs like HKQueryDescriptor, but it is not clear whether they provide any advantage over the observer plus anchored query approach for this use case. My main questions are: what is the recommended architecture for achieving near real-time syncing of HealthKit data for these metrics? Does HealthKit background delivery provide any guarantees or expectations around delivery timing, or can updates be significantly delayed depending on system conditions? How should edge cases be handled, such as when the device remains locked for long durations or when Low Power Mode is enabled? Would it be advisable to combine observer queries with BGTaskScheduler as a fallback mechanism? Finally, apps like Athlytic appear to show updated data immediately when opened. I am curious whether this is primarily achieved through background delivery or by fetching data on demand when the app becomes active. The goal is to design a system that is as close to real-time as possible while remaining reliable and compliant with iOS background execution constraints. Any recommended patterns, best practices, or references would be greatly appreciated.
Replies
1
Boosts
0
Views
364
Activity
May ’26
applicationWillTerminate to wrap up Background Recording
Hello together, the user is able to do recordings with my app. The recordings also runs, while the App is in Background. I have Background Modes Audio & Background enabled. When the user accidentally terminates the App while the recording is still running, the whole recording is lost. I tried AppDelegate applicationWillTerminate on my iOS 26 App and it works perfectly to wrap up the LiveActivity that is shown while the recording is active. But it does not save the Audio and also doesn't update the Widgets (they are interactive and show a different state while recording and stay stuck in recording-state on accidental termination). Any ideas? Best wishes, Dominik
Replies
2
Boosts
0
Views
368
Activity
May ’26
Recommended Architecture for Near-Real-Time Local Device Monitoring in Background
Hello, We are designing an iOS application for a vehicle safety use case. The app connects to a local network device (a DVR installed in the vehicle) and processes image frames to detect passenger-left-behind items, then alerts the driver if needed. We would like to better understand the recommended and App Store-compliant architecture for handling this scenario, especially when the app is not in the foreground. Current Requirements The app communicates with a local network device over Wi-Fi The device can provide image data The app performs or triggers AI inference based on the received data When a relevant event is detected, the app needs to notify the user (e.g., audio alert) Questions Background Execution Model For a near-real-time monitoring scenario, what architectural patterns are recommended on iOS when the app is running in the background? Background Modes Consideration In this type of use case, are any existing background modes (such as location or external accessory) considered appropriate when used strictly within their intended purpose? Enterprise / Managed Deployment Are there any specific entitlements or capabilities available in enterprise or commercial deployments that may allow more persistent local network communication under certain conditions?
Replies
1
Boosts
0
Views
169
Activity
Apr ’26
Safari web extensions: Optimal IPC architecture between extension and the containing app
I'm building a macOS safari extension and porting its functionality from a chrome extension. The chrome extension uses native messaging hosts to communicate with another process using IPC and holding a persistent connection. To use the same functionality in Safari, I understand that will need to use the handler to communicate it to the containing app, and the app will have to hold the persistent IPC connection. My question derives from that concept: should the app be running in a long-lived state? And if so, how can I ensure that app be running 100% of the time. Also is there any way I can control it's lifecycle with the Safari browser's lifecycle? I will not be using XPC here, but a different UDS to make the connection. Also in addition to that, what would you recommend the best approach is the communicate between the extension and it's handler? -> should it be again a UDS or userDefaults +darwin notification be enough? Also I wouldn't want the inter-message relayed between components to be dropped, is there a fault tolerant architecture you would recommend?
Replies
0
Boosts
0
Views
330
Activity
Apr ’26