# Guideline 2.5.1：公開API與SDK更新

> Guideline 2.5.1：只能用公開 API、要支援目前的 iOS、框架照用途使用。用 Expo 的話，先檢查原生模組。

原始頁面：[Guideline 2.5.1：公開API與SDK更新](https://devoria.fr/zh-hant/blog/guideline-2-5-1-public-api-sdk-expo)
作者：[Mehdi Azizi](https://devoria.fr/zh-hant/mehdi-azizi)
發布日期：2026-11-04
內容最後修訂：2026-11-04


Guideline 2.5.1 有四項要求：只能使用公開 API、要能在目前的 iOS 版本上執行、淘汰 Apple 已棄用的東西，以及每個框架都要用在它原本的用途上。**用 Expo 開發時，風險很少來自你的 JavaScript 程式碼，而是來自你安裝的原生模組，以及你編譯時用的 SDK。**

我用 Expo SDK 57 發布了 Solys、TradaZen 和 Nolera。Solys 依賴 Apple 的螢幕使用時間 API，這是一個用途受到限制的框架。這篇指南講的是審核規則。如果你是在上傳 build 時收到錯誤，請看 [ITMS-90338](https://devoria.fr/zh-hant/blog/itms-90338-non-public-api-usage-expo) 指南。同一章節裡的背景模式，請看 [guideline 2.5.4](https://devoria.fr/zh-hant/blog/guideline-2-5-4-background-mode-rejected) 指南。

## Guideline 2.5.1 說了什麼？

這條規則在 [App Review Guidelines](https://developer.apple.com/app-store/review/guidelines/#2.5.1) 的 2.5「Software Requirements」章節：「Apps may only use public APIs and must run on the currently shipping OS. Keep your apps up-to-date and make sure you phase out any deprecated features, frameworks or technologies that will no longer be supported in future versions of an OS. Apps should use APIs and frameworks for their intended purposes and indicate that integration in their app description.」

簡單說，四項義務：

1. **只能用公開 API**，也就是 Apple 有寫文件的 API。
2. **App 要能在目前的 iOS 版本上執行**，從 2026 年 9 月起是 iOS 27。
3. **不能留著即將消失的棄用功能**：Apple 宣布停止支援的東西，你要換掉。
4. **每個框架用在對的地方，並寫進描述裡**：HomeKit 用於智慧家庭，HealthKit 用於健康與運動，並連結到「健康」App。

所以退件標題才會是：「Guideline 2.5.1 - Performance - Software Requirements」。

## 公開 API：Expo App 的風險藏在哪裡

私有 API 是 Apple 沒有寫文件的系統函式。Apple 不保證它的行為，也不保證下一版 iOS 還有它，所以才禁止使用。

你的 JavaScript 程式碼從來不會直接碰到 iOS：它是透過原生模組。Expo SDK 裡的模組由 Expo 團隊維護。**其他模組則帶著不是你寫的程式碼，而 Apple 會像審你自己的程式碼一樣審它。** [ITMS-90683](https://devoria.fr/zh-hant/blog/itms-90683-missing-purpose-string-expo) 指南用權限說明文字示範了同樣的機制：Apple 判斷的是 build 裡有什麼程式碼，而不是 App 實際做了什麼。

以 Solys 為例，截至 2026 年 10 月 15 日，有 42 個直接相依套件包含原生 iOS 程式碼，其中 14 個不屬於 Expo SDK。包括 RevenueCat、Sentry、AppsFlyer，以及串接螢幕使用時間 API 的 `react-native-device-activity`。

私有 API 可能在兩個時間點被抓到。上傳時，App Store Connect 的自動分析可能回傳 ITMS-90338 錯誤。審核時，審核人員會引用 2.5.1。

## 棄用的 API：從 UIWebView 到 UIScene

最有名的例子是 UIWebView，以前用來顯示網頁的元件。Apple 從 2020 年 4 月起[不再接受](https://developer.apple.com/news/?id=12232019b)新 App 使用它，2020 年 12 月起連更新也不接受。只要有舊函式庫還引用它，上傳就會被擋下。在 Solys 上，用下面檢查清單的搜尋找不到任何引用。

下一個變動已經宣布了。Apple 的技術說明 [TN3187](https://developer.apple.com/documentation/technotes/tn3187-migrating-to-the-uikit-scene-based-life-cycle) 寫道：「In the next major release following iOS 26, UIScene lifecycle will be required when building with the latest SDK; otherwise, your app won't launch.」簡單說，用 iOS 27 SDK 編譯、但沒有採用場景生命週期的 App 會無法啟動。

三個要串起來看的日期：

- **從 2026 年 4 月起**，Apple 要求使用 Xcode 26：這是 [ITMS-90725](https://devoria.fr/zh-hant/blog/itms-90725-sdk-version-issue-expo) 指南的主題。
- **2027 年 4 月**，[Apple 的上傳頁面](https://developer.apple.com/app-store/submitting/)宣布 iOS 27 SDK 將成為必要條件。
- **Expo SDK 58** 從 2026 年 9 月 15 日起進入 beta，根據 [Expo 的公告](https://expo.dev/changelog/sdk-58-beta)，它已經會產生場景管理的程式碼。

用 Expo SDK 57 加 Xcode 26，你還是用 iOS 26 SDK 編譯：現在不會壞掉。**會修改 AppDelegate 的模組，必須在 2027 年 4 月前跟上。**

## 框架用在非預期用途

審核人員會確認敏感框架有對應到看得見的功能，而且你的商店頁面有提到。

- **HealthKit** 用於健康與運動。[Apple 的介面設計指南](https://developer.apple.com/design/human-interface-guidelines/healthkit)寫得很清楚：「If your app doesn't provide health and fitness functionality, don't request access to people's private health data.」
- **HomeKit** 用於智慧家庭，沒有別的用途。
- **PushKit** 用於 VoIP 通話。[PushKit 文件](https://developer.apple.com/documentation/pushkit/responding-to-voip-notifications-from-pushkit)說得很直白：「If you are unable to support CallKit in your app, you cannot use PushKit to handle push notifications.」用 VoIP 通知喚醒 App 卻沒有通話，就是濫用。
- **Family Controls**，也就是螢幕使用時間 API，需要特殊授權。它的[文件](https://developer.apple.com/documentation/familycontrols)寫明：「Before submitting your app to the App Store, you must request permission to use the entitlement.」

Solys 的這項發布授權，我在 2026 年 9 月 23 日申請，Apple 當天就核准了。用途和框架完全吻合：使用者選擇要暫停的 App，Solys 在起床後封鎖它們 30、45 或 60 分鐘。商店頁面的描述用一句話交代：「Solys 使用 Apple 的螢幕使用時間授權來暫停所選的 App。」**這正是 2.5.1 最後一句的要求：在描述中提到這項整合。**

## Beta 版本：TestFlight 可以，App Store 不行

[App Store Connect 的版本說明](https://developer.apple.com/help/app-store-connect/release-notes/)顯示了這條規則的實際運作。2026 年 10 月 14 日，用 Xcode 27.2 beta 3 建置的 build 被接受「for internal and external testing」，也就是用於 TestFlight。10 月 5 日，Xcode 27.1 RC 的 build 被接受「for the App Store」。

**用 Xcode beta 編譯的 build 可以進 TestFlight，但永遠不能送審。** 要送審，你需要正式版，或 Apple 已開放給 App Store 的 RC 版。

Expo App 要注意兩點：

- **Expo 的 beta 不等於 Apple 的 beta。** Apple 檢查的是 Xcode 和 iOS SDK 的版本，不是 Expo 的版本。SDK 58 的公告也補充說，搭載 Xcode 27 的 EAS 映像即將推出。
- **還是必須在目前的 iOS 上測試**，就算你用 iOS 26 SDK 編譯也一樣。在已更新的 iPhone 或模擬器上冷啟動 App。

## 檢查清單：送審前的原生相依套件

每次建置正式版 build 前都跑一遍。以下指令在 Expo 專案根目錄執行：

```bash
npx expo-doctor
npx expo install --check
grep -rlw "UIWebView" node_modules --include='*.m' --include='*.mm' --include='*.swift' --include='*.h'
```

1. **`npx expo-doctor` 沒有回報任何失敗。** Solys 在 2026 年 10 月 15 日的結果：21 項檢查通過 20 項。失敗是因為 13 個 Expo 套件落後一個修補版本，用 `npx expo install --check` 就能對齊。
2. **每個非 Expo SDK 的模組都列在 React Native Directory 上。** 根據 [Expo 文件](https://docs.expo.dev/versions/latest/config/package-json/)，Expo Doctor 預設就會做這項檢查。來路不明的套件，值得讀一下它的 iOS 程式碼。
3. **每個原生模組都跟得上你的 React Native 版本。** [Expo 版本對照表](https://docs.expo.dev/versions/latest/)把 SDK 57 對應到 React Native 0.86。好幾個版本都沒發布更新的模組，就是一個警訊。
4. **UIWebView 搜尋沒有任何結果。** Apple 宣布停止支援的其他 API 也照樣搜尋。
5. **每個敏感框架都有看得見的功能**：健康、螢幕使用時間、通話、家庭。描述有提到，特殊授權也已核准。
6. **Build 來自 Xcode 正式版。** 在 EAS 的建置日誌裡確認版本。
7. **App 能在目前的 iOS 版本上冷啟動**，並使用全新帳號。
8. **會動到 AppDelegate 的模組已宣布支援 UIScene**，在你升級到 iOS 27 SDK 之前。

## 如何回覆 2.5.1 退件？

訊息通常會點名有問題的 API 或框架。分兩種情況：

- **框架沒有任何看得見的用途**：移除該模組或功能，重新建置，再用兩句話回覆。
- **框架確實支撐某個功能**：提供確切的操作路徑、一張截圖或一段短影片，並在商店頁面描述中提到這項整合。

**移除原生模組會改變二進位檔：遠端更新是不夠的。** [guideline 2.1](https://devoria.fr/zh-hant/blog/app-store-guideline-2-1-rejection-fix) 指南解釋了為什麼審核人員只看得到內建在 build 裡的程式碼。接下來的溝通在 App Store Connect 裡進行，做法和[回覆 App Review](https://devoria.fr/zh-hant/blog/apple-resolution-center-reply-app-review-rejection) 指南一樣。

## 送出前檢查你的專案

[Review Kit](https://devoria.fr/zh-hant/kits/app-review) 收錄了我的送審前檢查清單、我修正過的退件，以及會幫你檢查 Expo 專案的 Claude Code skills。想要真人幫你看，[跟我預約一小時](https://devoria.fr/zh-hant/coaching)：我們一起讀 Apple 的訊息和你的相依套件。完整流程請看[被 Apple 退件的 App](https://devoria.fr/zh-hant/expertise/app-rejected-by-apple) 頁面。

正在準備第一次上架嗎？[做免費診斷](https://devoria.fr/zh-hant/diagnostic)：它會寄給你我的 Apple 防退件檢查清單。

## 常見問題

### 「Guideline 2.5.1 - Performance - Software Requirements」是什麼意思？

這是 Apple 認為你的 App 使用了非公開 API、棄用技術，或把框架用在非預期用途時的退件標題。訊息通常會點名有問題的項目。

### Guideline 2.5.1 和 ITMS-90338 錯誤有什麼差別？

ITMS-90338 是上傳 build 時，自動分析偵測到非公開符號所回傳的錯誤。2.5.1 則是由真人執行的審核規則，也涵蓋被濫用的框架和棄用技術。

### 可以送審用 Xcode beta 編譯的 App 嗎？

不行。App Store Connect 只接受這類 build 用於 TestFlight。要送審，請用 Xcode 正式版編譯，或 Apple 在版本說明中已開放給 App Store 的 RC 版。

### Expo App 會在不知情的情況下使用私有 API 嗎？

會，透過第三方原生模組。你的 JavaScript 程式碼本身不會呼叫 iOS，但每個原生套件都帶有 Objective-C 或 Swift 程式碼。每次發版前，都看一下非 Expo SDK 的模組清單。

### 需要馬上升級到 Expo SDK 58 嗎？

截至 2026 年 10 月 15 日，就 2.5.1 而言不需要：SDK 57 用 iOS 26 SDK 編譯，目前仍被接受。請在 2027 年 4 月前規劃升級，屆時 Apple 會要求 iOS 27 SDK 和場景生命週期。


## 你的專案

[Review Kit](https://devoria.fr/zh-hant/kits/app-review)：我的 App Store 審查檢查清單、我被 Apple 退件後的修正、Google Play 檢查清單，以及三個 Claude Code skill。$1,749。

[iOS & Android Kit](https://devoria.fr/zh-hant/kits/ios)：用 Claude Code 打造你的 iPhone 和 Android App：我自己 App 的起始程式碼、上架商店的完整流程，以及所有套件。$3,599。

[診斷：你離自己的 iPhone App 還差什麼](https://devoria.fr/zh-hant/diagnostic)：7 個問題，60 秒：找出真正卡住你發布 iPhone App 的原因，拿到你的 4 步驟路線，以及最適合你的套件。
