Understanding podspec Resource and resource_bundle Usage in CocoaPods

Mohit Bhalla
3 min readOct 17, 2023

CocoaPods is a widely used dependency management tool for iOS and macOS development. It allows developers to easily integrate third-party libraries into their projects. While you may already be familiar with using CocoaPods to include libraries and frameworks, you might not be aware of the powerful resource and resource_bundle features in the podspec file, which can help manage assets and resources more efficiently. In this blog post, we'll explore how to use these features and why they are valuable.

The Importance of Resources in Your CocoaPods

When developing an iOS or macOS application, you often need to include various resources like images, fonts, nibs, and other asset files. CocoaPods allows library authors to bundle resources with their libraries to provide a seamless integration experience for developers. However, without the proper handling of resources, conflicts and issues can arise, making it essential to use the resource and resource_bundle attributes in the podspec file.

The Basics: resource and resource_bundle

In a podspec file, you can specify resources that should be included with your CocoaPod. There are two primary ways to do this: by using the resource attribute and the resource_bundle attribute.

  1. resource Attribute: The resource attribute allows you to include individual files or folders as resources. You specify each resource by providing a path to the file or folder in your project. For example:
spec.resources = 'Assets/image.png', 'Assets/sounds'

This would include the ‘image.png’ file and the ‘sounds’ folder as resources in your CocoaPod.

2. resource_bundle Attribute: The resource_bundle attribute is used to include an entire bundle of resources. This can be especially useful for organizing related assets into a single package. Here's how to define a resource bundle:

spec.resource_bundles = {
'MySDK' => ['SDK/*/*.{xib,storyboard,xcassets}'] }

This would bundle all the assets inside the ‘Assets’ directory into a bundle named ‘MySDK’.

If you use resource or resources in a CocoaPods PodSpec file, you tell Cocoapods that these are the resource files your library will load during runtime

If your library is built as a dynamic framework, these files are just copied to the resource folder path of that framework and everything will be fine. Yet if your library is built as a static library, these are copied to the resource folder of the main application bundle (.app) and this can be a problem as this main application may already have a resource of that name or another Pod may have a resource of that name, in that case these files will overwrite each other. And whether a Pod is built as dynamic framework or as a static library is not specified by the PodSpec but in the Podfile by the application integrating your Pod.

Thus for Pods with resources, it is highly recommended to use resource_bundles instead!

spec.resource_bundles = {
'MySDK' => ['SDK/*/*.{xib,storyboard,xcassets}'] }

tell CocoaPods to create a resource bundle named MySDK (MySDK.bundle) and place all files matching the pattern into that resource bundle. If your Pod is built as a framework, this bundle is located in the resources folder of your framework bundle; if it is built as a static library, the bundle is copied to the resources folder of the main application bundle, which should be safe if you name your bundle the same way as your Pod.

This bundle will have the same identifier as your Pod, however when dynamic frameworks are built, your framework bundle will have that identifier as well and then it’s undefined behavior which bundle is being loaded when you load it by identifier (and currently the outer bundle always wins in my tests).

Now, it’s your turn. Go ahead and implement these strategies in your next project. Don’t forget to share your experiences and results in the comments below!

Happy coding and keep sharing :)

Other Post:

--

--

Mohit Bhalla

Principle Engineer iOS, Wynk, Airtel | ex Hindustan times