Introduction to On Demand Resources

An element of App Thinning

Introduction to On Demand Resources

An element of App Thinning

On-demand resources are app contents that are hosted on the App Store and are separate from the related app bundle that you download. They enable smaller app bundles, faster downloads, and richer app content. The app requests sets of on-demand resources, and the operating system manages downloading and storage. The app uses the resources and then releases the request. After downloading, the resources may stay on the device through multiple launch cycles, making access even faster.

On-demand resources work by assigning unique tags to resources within Xcode to create what’s called an asset pack. These packs can include anything from asset catalogs (images, SpriteKit textures, data, etc.) or even just other files, such as OpenGL and Metal shaders as well as SpriteKit and SceneKit scenes and particle systems.

When you submit your app to the App Store, these resources are also uploaded and are hosted there in order to be downloaded at any time. To download asset packs at runtime in an app, you simply use the tag for each pack that you assigned in Xcode.

The resources can be of any type supported by bundles except for executable code.

Note: A data file can contain any sort of data except for executable Swift, Objective-C, C, or C++ code. Files generated by scripting languages can be on-demand resources.

Features

  • Dynamically loaded content Hosted on the App Store.
  • Downloadable during app install and by request.
  • Automated downloads before first launch.
  • Prioritized downloads
  • Intelligent content caching.
  • Max app size with On Demand Resources increases to 20GB
References: https://developer.apple.com/videos/

Benefits of On-Demand Resources

  • Better install experience, Smaller main app bundle: Faster initial download
  • Greater, richer app content : Up to 20-GB available on demand
  • More apps installed and ready to run : Reduces need to manage storage
  • Lazy loading of app resources.
  • Remote storage of in-app purchase resources
  • Remote storage of rarely used resources.

On-demand resource types

Below image shows supported on-demand resource types and indicates whether those types are included in the target as a file or in an asset catalog.

Reference: developer.apple.com

TAG Categories

The two main aspects of an app that uses on-demand resources are the app bundle, which is full of executable code for your app and essential assets, such as user interface icons, and asset packs.

For these asset packs, there are three main categories which you can organize in Xcode.
The default category for a tag is Download Only On Demand. The view displays the tags grouped by their prefetch category and the total size for each category. The size is based on the device that was the target of the last build. Tags can be dragged between categories.

  • Initial install tags. This is for content that is needed for your app to run for the first time, but that can be deleted later. The resources are downloaded at the same time as the app. The size of the resources is included in the total size for the app in the App Store. The tags can be purged when they are not being accessed by at least one NSBundleResourceRequest object.
  • Prefetch tag order. This category includes content that you want to be downloaded immediately after your app has finished installing.The resources start downloading after the app is installed. The tags will be downloaded in the order in which they are listed in the Prefetched tag order group.
  • Dowloaded only on demand. This category is aimed at content that you need at a later time and your app can function without. The tags are downloaded when requested by the app.

Enabling On-Demand Resources

On-demand resources are enabled by default for apps targeting iOS 9.0 or later. You can manually change this in the build settings for a target.

Figure : Enable on-demand resources build setting

Setting enable or disable on-demand resources

  1. In the project navigator, select the project file.
  2. In the project editor, select the target.
  3. Select the Build Settings pane.
  4. Show the Assets category.
    TIP: To quickly locate the Assets category, type Assets into the search field in the upper right of the Build Settings pane.
  5. Set the value of the Enable On-Demand Resources setting.
  • Yes enables on-demand resources for the target.
  • No disables on-demand resources for the target.

OTHER BUILD SETTINGS IN THE ASSETS CATEGORY

For information on the other build settings in the pane, see:

Creating and Assigning Tags

Tags are used to identify and manage sets of on-demand resources. Assigning one or more tags to a resource in your project identifies it as an on-demand resource. At runtime, all calls for managing on-demand resources work with tags, not individual resources.

To create a new tag

  1. In the project navigator, select the project file.
  2. Open the project editor for the target for the new tag.
  3. Select the Resource Tags pane.
  4. Click the Add button (+) in the upper-left corner of the pane.
  5. A new tag entry appears.

The On-Demand Resource Tags field is a quick way to view, add, and delete tags for a file, folder, or resource. For files and folders in the Project navigator, the field is shown in the File inspector. The field is enabled for folders or for any types of files that can be tagged, as shown in Figure .

Resource tags field for a file

In an asset catalog, the field is shown in the Attributes inspector for folders or for any types of assets that can be tagged, as shown in Figure.

Resource tags field for an asset catalog item

Hosting On-Demand Resources

You can host on-demand resources on any compliant web server with the Apple app transport security requirements. This includes having an SSL connection with a valid certificate signed by an appropriate authority.

The General form of the the URL is : <protocol>://<path-to-asset-packs>/

The URL end with forward slash (/).

For example if your hosting server URL is “www.weblineindia.com” and tag directory is apps/myapp/tags/ then On-Demand resource URL will be “www.weblineindia.com/apps/myapp/tags/”

Set the hosting URL to the target.

  • Select the project file from the project navigator.
  • Select the target from the project editor.
  • Select the build setting pane.
  • Show the Assets category.
  • Set the value of the Assets Pack Manifest URL prefix setting to the URL for the hosted assets packs.

Generate Assets Pack

  • Generate Archive of the Project.
  • Once the Organizer screen is open, select archive and click on Export button.
  • Select proper method for export and click on next button.
  • Choose your Development team.
  • Select compatible device type for archive and click on next.
  • Here you will see new window “On-Demand Resources”. In which select “Host resources on server” and enter URL for On demand resources. In our case it will be www.weblineindia.com/apps/myapp/tags/ and click on next.
  • Once build is generated, Xcode opens the exported app folder by default. The assets packs are in the OnDemandResources folder.
  • Now upload all the assets pack on the server.

Platform Sizes for On-Demand Resources

The total size for the resources in a tag can be no more than 512 MB after app slicing. The total size for the on-demand resources stored on the app store for an app can be no more than 20 GB. The total size limit for the on-demand resources associated with an app are in addition to the size limit for the app bundle downloaded by the user.

The ideal size of a tag is less than or equal to 64 MB. This size provides a good balance between download speed and local storage to make available for purging when the local storage for the device is low.

There are limits on the amount of storage used by on-demand resources at App Store submission time and while the app is running.

Reference: https://developer.apple.com/ (On-demand resource sizes)

Accessing and Downloading On-Demand Resources

An app uses NSBundleResourceRequest to:

  • Request access to on-demand resources
  • Inform the operating system when access is no longer needed
  • Update the priority of a download
  • Track the progress of a download
  • Check for a notification of low disk space

You use other methods in NSBundle to set the preservation priority in local storage of the downloaded resources.

Requesting Access

The app must request access to a tag before using any of the tag’s associated resources by initializing an NSBundleResourceRequest instance. The first step is to create an NSBundleResourceRequest object for the tags. A tag can be managed by multiple NSBundleResourceRequest objects.

Initializing an NSBundleResourceRequest Instance

  • Use initWithTags: if all of the resources associated with the tags are in the main bundle.
  • Use initWithTags:bundle: if all of the resources associated with the tags are in the same custom bundle.

Requesting Access to the Tags

You can use one of two methods to request access to resources. The main difference between the methods is how they respond if the resources are not on the device:

Each method takes a callback block that is called with the result of the access request. All of the associated resources will be on the device when the callback is invoked with a successful result.

Checking Whether Tags Are Already on the Device

conditionallyBeginAccessingResourcesWithCompletionHandler: grants access if the tags are already on the device. If the tags are not on the device, the app needs to call beginAccessingResourcesWithCompletionHandler: to download them.

Downloading and Downloading Priority

The loadingPriority property of a resource request is used by the operating system as a hint for prioritizing the order of your download requests. Requests with a higher value for loadingPriority are loaded before ones with a lower value.

Tracking Download Progress

Soon after a download begins, the resource request starts updating progress, a property of type NSProgress. The app tracks download progress using key-value observing (KVO) on the fractionCompleted property of progress. This requires that you start and stop observation and add code that executes when the value changes.

Ending Access

Ending access when the app has finished using a resource request allows the operating system to release the storage on the device. If there are no other resource requests using the same storage, the operating system can reclaim the storage if needed.

Low-Space Warning

The operating system sends out the NSBundleResourceRequestLowDiskSpaceNotification notification if it is unable to free up enough storage space for the current resource request. Your app should stop accessing any tags that are not required, as described in Ending Access

Setting Preservation Priority

The preservation priority of a tag provides a hint to the operating system about the relative importance of keeping the associated resources in local storage. When the operating system needs to purge tags, it starts with the lowest preservation priority. You can set a high-preservation priority for tags that contain resources that are more important than others such as an in-app purchase, or resources for functionality that is used more frequently.

Conclusion

On-demand resources in iOS 9 or later and tvOS is a great way to reduce the size of your app and deliver a better user experience to people who download and use your application. While it’s very easy to implement and set up, there are quite a few details that you must keep in mind in order for the whole on-demand resources system to work flawlessly without excessive loading times and unnecessarily purging data.

For more articles:

References:

  1. https://developer.apple.com/library/archive/documentation/FileManagement/Conceptual/On_Demand_Resources_Guide
  2. https://developer.apple.com/videos/
  3. https://www.technetexperts.com/mobile/enabling-on-demand-resources-in-ios-application-development/