Privacy Manifests

Apple Privacy Manifests and Required Reason APIs

A privacy manifest, PrivacyInfo.xcprivacy, is a property list in an app or SDK that declares the data it collects, whether it tracks users, and why it calls any required reason API: UserDefaults, file timestamps, system boot time, free disk space and a few more, all usable to fingerprint a device. Since 1 May 2024 App Store Connect 10 has rejected uploads that call one without an approved reason code. In a React Native 36,878 app the calls come mostly from libraries, which ship their own manifests, and you can count them without a Mac:

Finding the privacy manifests and API categories in BookNest's dependenciesJSX
find node_modules -name PrivacyInfo.xcprivacy -not -path "*/example/*" | wc -l
find node_modules -name PrivacyInfo.xcprivacy -not -path "*/example/*" -exec cat {} + \
  | grep -o 'NSPrivacyAccessedAPICategory[A-Za-z]*' | sort | uniq -c | sort -rn
Output
15
     10 NSPrivacyAccessedAPICategoryFileTimestamp
      5 NSPrivacyAccessedAPICategoryUserDefaults
      4 NSPrivacyAccessedAPICategorySystemBootTime
      2 NSPrivacyAccessedAPICategoryDiskSpace

Expo 6,418 's documentation warns that Apple does not read every manifest in static CocoaPods 66,002 libraries, which React Native's are, so copy their reasons into the app's own manifest. BookNest's ios.privacyManifests in app.json lists an NSPrivacyAccessedAPITypes entry for each of the four categories with the union of its libraries' reason codes, such as CA92.1 (the app reads its own defaults) and 35F9.1 (measuring elapsed time). npx expo prebuild --platform ios --no-install runs on Linux, since it only writes files, and it produced ios/BookNest/PrivacyInfo.xcprivacy with the four categories, NSPrivacyTracking set to false, and ITSAppUsesNonExemptEncryption in Info.plist. What BookNest sends to its server (account, orders, push token) goes in App Store Connect's App Privacy answers. A missing reason earns an email naming the API (ITMS-91053).