Вашу сборку для iOS отклонили. Исправьте и загрузите снова без Mac
Apple прислала письмо или загрузка не прошла, а Mac у вас нет. Сначала проверьте, нужна ли для исправления новая сборка. Иногда нет. Для случаев, где она нужна, здесь есть исправление и команды, чтобы за один день собрать архив, экспортировать и загрузить его снова.
Нужна ли новая сборка?
Не каждая проблема означает пересборку. Эти исправления делаются в App Store Connect из любого браузера:
- Скриншоты, описание и другой текст страницы продукта.
- Ответы об экспортном контроле для сборки со статусом Missing Compliance.
- Ваши ответы в разделе App Privacy в App Store Connect.
Другим исправлениям нужна новая сборка, а значит, Xcode на Mac. Это старый Xcode или SDK, манифест конфиденциальности, строки в Info.plist и изменения в коде или SDK. Каждой новой загрузке также нужен больший номер сборки.
1. Собрано слишком старым Xcode
С 28 апреля 2026 года Apple принимает только загрузки, собранные в Xcode 26 или новее с SDK для iOS 26. Сборка из Xcode 16 это правило не проходит. Чтобы узнать, чем собран архив, прочитайте два ключа из его приложения:
/usr/libexec/PlistBuddy -c 'Print :DTSDKName' -c 'Print :DTXcode' \ MyApp.xcarchive/Products/Applications/MyApp.app/Info.plist
На раннере GitHub macos-26 это вывело iphoneos26.5 и 2660, то есть Xcode 26.6. На Mac от MacRun по умолчанию стоит Xcode 27.1, и Xcode 26.6 тоже есть. Оба проходят правило.
Одна оговорка: по словам Apple, приложениям на SDK iOS 27.1 с апреля 2027 года понадобятся скриншоты iPhone Duo. Наше руководство по iPhone Duo показывает, как их сделать.
2. Манифест конфиденциальности и API с обязательной причиной
Для некоторых API нужна указанная причина, например для UserDefaults и меток времени файлов. Причины пишутся в файл PrivacyInfo.xcprivacy. С 1 мая 2024 года App Store Connect не принимает приложения, которые это пропускают. Apple также отклоняет манифесты с неожиданными ключами. В её письме указан путь к каждому плохому файлу.
Вот минимальный манифест для приложения, которое читает свои UserDefaults. CA92.1 это код причины Apple для такого использования:
<?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>NSPrivacyTracking</key>
<false/>
<key>NSPrivacyTrackingDomains</key>
<array/>
<key>NSPrivacyCollectedDataTypes</key>
<array/>
<key>NSPrivacyAccessedAPITypes</key>
<array>
<dict>
<key>NSPrivacyAccessedAPIType</key>
<string>NSPrivacyAccessedAPICategoryUserDefaults</string>
<key>NSPrivacyAccessedAPITypeReasons</key>
<array>
<string>CA92.1</string>
</array>
</dict>
</array>
</dict>
</plist>Добавьте его в цель приложения. Потом проверьте, что он корректен. Мы запустили эти команды на хорошем файле и на сломанном:
$ plutil -lint MyApp/PrivacyInfo.xcprivacy MyApp/PrivacyInfo.xcprivacy: OK $ plutil -lint bad.xcprivacy bad.xcprivacy: (Value missing for key inside <dict> at line 1)
После архивации файл должен лежать в корне .app. У нас так и было. Если в письме указан сторонний SDK, обновите этот SDK. Его собственный манифест должен покрывать его собственное использование API.
3. Нет строк описания доступа
Если приложение использует камеру, фото или геопозицию, в Info.plist для этого нужна строка с целью. По словам Apple, без неё доступ не работает, и приложение может упасть. Правило App Review 5.1.1(ii) также требует, чтобы строка ясно описывала, как вы используете данные.
<key>NSCameraUsageDescription</key> <string>Scan receipts to add them to your expenses.</string>
Проверяйте собранное приложение, а не только исходный файл:
plutil -extract NSCameraUsageDescription raw \ MyApp.xcarchive/Products/Applications/MyApp.app/Info.plist
4. Экспортный контроль
Сборка без ответа о шифровании показывает Missing Compliance в TestFlight. Пересборка для этого не нужна. Откройте сборку в App Store Connect, нажмите Manage и ответьте на вопросы. Чтобы в следующий раз их пропустить, добавьте этот ключ в Info.plist. Ставьте false, только если ваше шифрование освобождено от контроля, например обычный HTTPS:
<key>ITSAppUsesNonExemptEncryption</key> <false/>
5. Неверные или отсутствующие скриншоты
Скриншотам пересборка не нужна, но нужен правильный размер. Apple требует хотя бы один скриншот iPhone в размере среднего дисплея с Dynamic Island. Это 1179 x 2556 или 1206 x 2622 пикселя в портретной ориентации. Если iPhone под рукой нет, их делает симулятор:
xcrun simctl boot "iPhone 17 Pro" xcrun simctl install "iPhone 17 Pro" MyApp.app xcrun simctl launch "iPhone 17 Pro" com.example.myapp xcrun simctl io "iPhone 17 Pro" screenshot shot.png sips -g pixelWidth -g pixelHeight shot.png
Наш скриншот с iPhone 17 Pro вышел размером 1206 x 2622, это нужный размер. iPhone 17 Pro Max дал 1320 x 2868, это подходит для большого набора. Выполните xcrun simctl list devices available, чтобы увидеть, что установлено.
Пересборка и загрузка
Увеличьте номер сборки, потом соберите архив. На нашем тестовом раннере этот шаг занял 12 секунд для маленького приложения на SwiftUI:
xcodebuild archive -project MyApp.xcodeproj -scheme MyApp \ -destination 'generic/platform=iOS' \ -archivePath build/MyApp.xcarchive \ MARKETING_VERSION=1.0.1 CURRENT_PROJECT_VERSION=3
Дальше экспортируйте подписанный .ipa. Запишите это в ExportOptions.plist со своим Team ID. Ключи взяты из xcodebuild -help:
<?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>method</key> <string>app-store-connect</string> <key>teamID</key> <string>ABCDE12345</string> <key>signingStyle</key> <string>automatic</string> </dict> </plist>
xcodebuild -exportArchive -archivePath build/MyApp.xcarchive \ -exportOptionsPlist ExportOptions.plist -exportPath build/export \ -allowProvisioningUpdates
Сначала войдите в Xcode со своим Apple Account. У нашего тестового архива без подписи не было команды, и экспорт остановился с ошибкой "error: exportArchive No Team Found in Archive".
На странице Apple про загрузку перечислены Xcode, Transporter и altool. С altool один раз сохраните пароль приложения в связке ключей. Потом проверьте и загрузите:
xcrun altool --store-password-in-keychain-item altool -u you@example.com -p xxxx-xxxx-xxxx-xxxx xcrun altool --validate-app -f build/export/MyApp.ipa -t ios -u you@example.com -p @keychain:altool xcrun altool --upload-app -f build/export/MyApp.ipa -t ios -u you@example.com -p @keychain:altool
Или укажите destination со значением upload в ExportOptions.plist. Тогда -exportArchive сам отправит сборку в App Store Connect. Наше руководство по публикации описывает API-ключи и TestFlight.
Исправьте всё за один день
Суточный доступ MacRun стоит $15, оплата один раз, без продления. Это выделенный Mac mini на M6, готовый меньше чем за 5 минут. Установлены Xcode 27.1 и Xcode 26.6, а также симулятор iOS 27.1. Вы подключаетесь через Tailscale по SSH или через VNC-клиент. Если проверка снова вернёт сборку, неделя стоит $59. В конце Mac очищается, поэтому сначала отправьте код в репозиторий.
Кому не стоит арендовать для этого Mac
- Если исправить нужно скриншоты, текст или ответы об экспорте, используйте App Store Connect в браузере.
- Приложения на Expo можно пересобрать через EAS Build на машинах Expo с macOS. Смотрите руководство сборка iOS-приложений на Windows.
- Если вы уже собираете в Codemagic или GitHub Actions, отправьте исправление и дайте CI пересобрать.
Частые вопросы
Можно ли исправить отказ App Store без Mac?
+
Иногда. Скриншоты, текст и ответы об экспортном контроле исправляются в App Store Connect из любого браузера. Новый Xcode, манифест конфиденциальности или изменение Info.plist требуют новой сборки, а для неё нужна macOS.
Какую версию Xcode требует App Store Connect в 2026 году?
+
С 28 апреля 2026 года Apple требует загрузки, собранные в Xcode 26 или новее с SDK для iOS 26. На Mac от MacRun по умолчанию стоит Xcode 27.1, и Xcode 26.6 тоже установлен.
Как добавить манифест конфиденциальности в iOS-приложение?
+
Добавьте в цель приложения файл PrivacyInfo.xcprivacy. Перечислите каждую категорию API с обязательной причиной и код причины Apple, например CA92.1 для собственных UserDefaults приложения. Проверьте файл через plutil -lint и пересоберите.
Моя сборка в TestFlight пишет Missing Compliance. Нужно пересобирать?
+
Нет. Откройте сборку в App Store Connect, нажмите Manage и ответьте на вопросы о шифровании. Чтобы пропустить их, добавьте ITSAppUsesNonExemptEncryption в Info.plist в следующей сборке.
Какой размер скриншотов App Store требует для iPhone?
+
Apple требует хотя бы один скриншот для iPhone с Dynamic Island и средним дисплеем: 1179 x 2556 или 1206 x 2622 пикселя в портретной ориентации. Наш скриншот из симулятора iPhone 17 Pro был 1206 x 2622.
Как загрузить новую сборку без окна Xcode?
+
Экспортируйте .ipa через xcodebuild -exportArchive, потом выполните xcrun altool --upload-app. Transporter тоже подходит. Apple перечисляет оба способа на своей странице про загрузку.