Read the lockfiles. For CocoaPods, Podfile.lock records the exact version of every pod installed. For Swift Package Manager, the resolved packages file records pinned versions. Then check the project for frameworks added by hand, because no lockfile knows about those.
Where each ecosystem keeps the list
| Source of code | Where the exact versions live | Commit it? |
|---|---|---|
| CocoaPods | Podfile.lock | Yes, per the CocoaPods guide |
| Swift Package Manager | Package.resolved | Commit it for apps, check Apple's docs for your Xcode version |
| Carthage or manual frameworks | Your own records | Write them down |
| Cross-platform plugins | Their own lockfile plus the pods or packages they bring | Yes |
The CocoaPods guide says the Podfile and Podfile.lock should always be kept under version control. It also says pod install honors the versions in the lockfile, while pod update re-resolves and writes a new one.
What a lockfile does not tell you
A lockfile lists what the package manager resolved. It does not list:
- binary frameworks you dragged into the project,
- code vendored by copy and paste,
- SDKs that download or load code at runtime, which Apple restricts in its review guidelines.
Apple's guideline 2.5.2 says apps should be self-contained in their bundles and may not download, install or execute code that introduces or changes features or functionality. That is a rule for the app, and also a hint for your inventory: what is in the bundle is what you ship.
Steps
- Open the project and list its package manager files.
- Read Podfile.lock and the resolved packages file for exact versions.
- Open the Frameworks section of the build to find binary frameworks not covered by either.
- For each binary framework, note the vendor and version.
- Combine the lists into one inventory, or generate an SBOM from the project.
- Re-run this at every release.
Why pods and packages need separate attention
A single app often uses both. A pod can pull in other pods, and a Swift package can bring in packages of its own. Direct dependencies are a short list. The full tree is often several times longer, and advisories land on the long list.
For pinning and update behavior in Swift, see Swift Package Manager dependency resolution and pinning. For CocoaPods registry risks, see CocoaPods supply chain security and Podfile.lock integrity.
Try it yourself
Click through it at your own pace, or open it full screen.
Open a package in the demo and look for what depends on it. That reverse view is how you decide who must update.
Quick check
Should Podfile.lock be committed?
Yes. The CocoaPods guide says the Podfile and Podfile.lock should always be kept under version control.
Does a lockfile include binary frameworks I added manually?
No. Track those separately.
Safeguard scans dependency manifests and SBOMs and matches components against known vulnerabilities. It does not inspect compiled iOS binaries. You can start with a free scan.
Sources
Last reviewed: 19 October 2026.