I did further investigation and that's step by step I did:
- Created manifest file:
{
"assetPackID": "assettest",
"downloadPolicy": {
"onDemand": {}
},
"fileSelectors": [
{
"file": "audio/test_audio.mp3"
}
],
"platforms": [
"iOS"
]
}
- Created package assettest and upload it to AppStore Connect via Transporter (verified, delivered, ready for internal testing)
xcrun ba-package Manifest.json -o assettest.aar
- Created new target ManagedAssetPack (Apple-Hosted). BackgroundDownloadHandler file is:
import BackgroundAssets
import ExtensionFoundation
import StoreKit
@main
struct DownloaderExtension: StoreDownloaderExtension {
func shouldDownload(_ assetPack: AssetPack) -> Bool {
// Use this method to filter out asset packs that the system would otherwise download automatically. You can also remove this method entirely if you just want to rely on the default download behavior.
return true
}
}
-
Created appgroup and successfully associated main app target and background assets target (I have 3 flavors in main app, Signing&Capabilities tab has no errors, Provisioning profiles has no errors)
-
Info.plist for main target:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>BAAppGroupID</key>
<string>***mygroup***</string>
<key>BAHasManagedAssetPacks</key>
<true/>
<key>BAUsesAppleHosting</key>
<true/>
<key>CFBundleDevelopmentRegion</key>
<string>$(DEVELOPMENT_LANGUAGE)</string>
<key>CFBundleExecutable</key>
<string>$(EXECUTABLE_NAME)</string>
<key>CFBundleIdentifier</key>
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>$(PRODUCT_NAME)</string>
<key>CFBundlePackageType</key>
<string>$(PRODUCT_BUNDLE_PACKAGE_TYPE)</string>
<key>CFBundleShortVersionString</key>
<string>$(MARKETING_VERSION)</string>
<key>CFBundleVersion</key>
<string>$(CURRENT_PROJECT_VERSION)</string>
<key>ITSAppUsesNonExemptEncryption</key>
<false/>
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsArbitraryLoads</key>
<true/>
</dict>
<key>UIApplicationSceneManifest</key>
<dict>
<key>UIApplicationSupportsMultipleScenes</key>
<false/>
</dict>
<key>UIBackgroundModes</key>
<array>
<string>audio</string>
<string>processing</string>
</array>
<key>UILaunchScreen</key>
<dict>
<key>UIImageName</key>
<string>LaunchImage</string>
</dict>
<key>UISupportedInterfaceOrientations</key>
<array>
<string>UIInterfaceOrientationPortrait</string>
<string>UIInterfaceOrientationPortraitUpsideDown</string>
<string>UIInterfaceOrientationLandscapeLeft</string>
<string>UIInterfaceOrientationLandscapeRight</string>
</array>
</dict>
</plist>
- Swift file:
import Foundation
import BackgroundAssets
import os.log
@MainActor
class SimpleAssetPackTest: ObservableObject {
static let shared = SimpleAssetPackTest()
private let logger = Logger(subsystem: "mypackagename", category: "SimpleAssetPackTest")
private init() {}
func testAssetPack() async {
logger.error("ASSETPACKTESTLOG: 🧪 Starting asset pack test")
// Step 1: Try to get the assettest pack
logger.error("ASSETPACKTESTLOG: 🧪 Getting assettest asset pack...")
do {
let assetPack = try await AssetPackManager.shared.assetPack(withID: "assettest")
logger.error("ASSETPACKTESTLOG: 🧪 Asset pack retrieved: \(assetPack.id)")
// Step 2: Start download and WAIT for it
logger.error("ASSETPACKTESTLOG:🧪 Starting download...")
do {
try await AssetPackManager.shared.ensureLocalAvailability(of: assetPack)
logger.error("ASSETPACKTESTLOG: ✅ Download completed!")
} catch {
logger.error("ASSETPACKTESTLOG: ❌ Download failed: \(error)")
return
}
// Step 3: Try to access file after download
logger.error("ASSETPACKTESTLOG: Trying to access file after download...")
do {
let audioData = try AssetPackManager.shared.contents(at: "audio/test_audio.mp3", searchingInAssetPackWithID: "assettest")
logger.error("ASSETPACKTESTLOG: ✅ SUCCESS! Audio file accessed: \(audioData.count) bytes")
} catch {
logger.error("ASSETPACKTESTLOG: ❌ File not available after download: \(error)")
}
} catch {
logger.error("ASSETPACKTESTLOG: ❌ Failed to get asset pack: \(error)")
}
}
}
LOGS AT THE END:
ASSETPACKTESTLOG: 🧪 Asset pack retrieved: assettest
ASSETPACKTESTLOG:🧪 Starting download...
It seems ensureLocalAvailability returns nothing or hangs out.
Other important things:
- testing device iPhone 12 (iOS 26.1 beta 4)
- macOS Tahoe 26.1
- xCode Beta 26.1 beta 3
- Tested on AppStore Connect, also locally
Any suggestion?