Team-scoped keys introduce the ability to restrict your token authentication keys to either development or production environments. Topic-specific keys in addition to environment isolation allow you to associate each key with a specific Bundle ID streamlining key management.
For detailed instructions on accessing these features, read our updated documentation on establishing a token-based connection to APNs.
Delve into the world of built-in app and system services available to developers. Discuss leveraging these services to enhance your app's functionality and user experience.
Selecting any option will automatically load the page
Post
Replies
Boosts
Views
Created
Hello,
I recently paid for the Apple Developer Program membership, but I am still being prompted to complete payment as if my subscription has not been processed.
I have already been charged, and the payment appears to have gone through on my end. However, my account still shows an unpaid or inactive status, and I continue to receive payment prompts.
Could you please investigate this issue and confirm that my membership is active? If there is a duplicate charge or a processing error, I would appreciate your assistance in resolving it.
Thank you for your help.
Topic:
App & System Services
SubTopic:
General
We are implementing in-app provisioning in our fintech app;
We are reaching out to ask for your help in understanding what is going wrong so we can fix it.
What happens:
User taps “Add to Apple Wallet” → we present PKAddPaymentPassViewController → they tap Next → after a few seconds the flow fails with "Set Up Later" alert.
Device log:
"eligibility request failure",
"Received HTTP 500"
)'; underlyingError: 'Error Domain=PKPaymentWebServiceErrorDomain Code=0 "Unexpected error." UserInfo={PKErrorHTTPResponseStatusCodeKey=500, NSLocalizedDescription=Unexpected error.}'; userInfo: '{
PKErrorHTTPResponseStatusCodeKey = 500;
}'; >
Feedback Assistant ID: FB22176928 (In-App Provisioning issue 500 Internal Server Error)
I am working on an e-commerce app (retail/marketplace) that allows users to place orders for both free and paid products. After receiving a DeclaredAgeRange API response — retrieved via the Family Controls / Screen Time framework — indicating that a user is a minor, I want to understand the recommended approach for handling payment flows.
Specifically, is it necessary to block payments for users identified as minors via DeclaredAgeRange, even though our app uses server-side encrypted card processing rather than Apple In-App Purchases (StoreKit)?
Any guidance on best practices or App Store policy requirements for this scenario would be greatly appreciated.
I am working on an e-commerce app (retail/marketplace) that allows users to place orders for both free and paid products. After receiving a DeclaredAgeRange API response — retrieved via the Family Controls / Screen Time framework — indicating that a user is a minor, I want to understand the recommended approach for handling payment flows.
Specifically, is it necessary to block payments for users identified as minors via DeclaredAgeRange, even though our app uses server-side encrypted card processing rather than Apple In-App Purchases (StoreKit)?
Any guidance on best practices or App Store policy requirements for this scenario would be greatly appreciated.
Hello,
I have a question regarding how prorated refunds are reflected when a user upgrades a subscription.
From my understanding, when a user upgrades to a higher-tier subscription, the remaining value of the current subscription is refunded as a prorated amount, typically represented as REFUND_PRORATED or PRORATED_CREDIT.
However, when reviewing the available transaction history and refund-related data (including the App Store Server API and transaction history endpoints), I cannot find any field or record that clearly indicates:
the actual prorated refund amount, or
the credit applied when upgrading to another subscription
In other words, while the concept of REFUND_PRORATED seems to exist conceptually, I cannot identify where the actual prorated value or credit applied to the upgrade is exposed in the transaction or refund history.
My questions are:
Is there any way to retrieve the actual prorated refund or credit amount when a user upgrades a subscription?
Is this information available through the App Store Server API (e.g., Get Transaction History) or any other API endpoint?
If not, is there any recommended method to determine how much of the previous subscription was credited toward the upgraded subscription?
Any clarification would be greatly appreciated.
Thank you for your help.
Topic:
App & System Services
SubTopic:
StoreKit
We have a macOS system extension with NETransparentProxyProvider which is able to intercept traffic and handle it. We also wanted to setup few search domains from our network extension. However, unlike PacketTunnelProvider, NEDNSSettings are completely ignored with NETransparentProxyProvider.
So whats the best way to setup few DNS search domains when using NETransparentProxyProvider.
Hello, I have an application that needs to be published to the App Store.
This application consists of two processes, A and B, where B is a child process of A.
I found that if process B needs to be launched as a child process of A in sandbox mode, it is necessary to set the following keys in the entitlements.plist file:
<key>com.apple.security.app-sandbox</key><true/><key>com.apple.security.inherit</key><true/>
However, after setting these keys, process B can no longer be launched directly.
This issue is particularly prominent because process B has a window and a Dock icon — in this case, if the user pins the Dock icon, they will be unable to launch process B.
Could you please advise on a solution to this problem?
Hey everyone,
I found a possible SwiftData Release-only issue with nested sort descriptors on an optional relationship.
In a minimal repro, sorting a @Query by a nested optional relationship key path like:
SortDescriptor(\InvestigationPhotoAsset.imageAnalysis?.overallAestheticsScore, order: .reverse)
works in Debug, but crashes at runtime in Release.
The surprising part is that the crash depends on file layout:
if the active SwiftData models and the sort logic are kept in the same Swift file, the app works
if the same models are split into separate files, the Release build crashes, 'Debug' will also work
The repro was reduced to just two SwiftData models:
InvestigationPhotoAsset
InvestigationImageAnalysis
So this looks less like an app-modeling issue and more like a SwiftData/compiler/codegen issue related to nested sort metadata in optimized builds.
If useful, I can also give you a slightly more formal version with a title and code snippet block.
Please check out the code example here
Has anyone faced something similar?
Bug is reported as FB22173905
Hi,
I am currently implementing a recurring payment feature using the Apple Pay JS API.
Based on the official demo (https://applepaydemo.apple.com/apple-pay-js-api), it appears that the recurringPaymentRequest object only supports a maximum of two stages: trialBilling and regularBilling.
However, our service requires a multi-stage billing model with three or more different cycles/amounts as shown below:
Example Schedule:
Stage 1: 2,000 JPY (2026-03-01 to 2026-04-01)
Stage 2: 1,500 JPY (2026-04-01 to 2026-10-01)
Stage 3: 1,000 JPY (2026-10-01 to 2027-10-01)
Stage 4: 500 JPY (Thereafter)
Questions:
Is there any way to directly define and display three or more different billing cycles/amounts on the Apple Pay payment sheet?
If the API is strictly limited to two stages, what is the Apple-recommended way to provide transparency for such complex schedules while remaining compliant with the guidelines? For instance, is it acceptable to set the final amount in regularBilling and explain the preceding stages in the billingAgreement or paymentDescription fields?
I would appreciate any insights or official guidance on this.
Best regards,
Topic:
App & System Services
SubTopic:
Apple Pay
Hello,
We are experiencing an issue related to push notifications after updating devices to iOS 26.4 Beta.
Our system stores push notification tokens on the server by associating the device token with the device’s IDFV in the app.
After updating a device to iOS 26.4 Beta, we observed that the device token from a previously uninstalled version of the app remains valid for more than a week. As a result, two push notifications are delivered to the same device.
The situation is as follows:
The user installs the app and a device token is generated.
The user uninstalls the app.
Later, the user installs the app again and a new device token is generated.
However, the previous device token does not become invalid, even after more than a week.
Because IDFV changes when the app is reinstalled, our server cannot determine that the device belongs to the same user. Therefore, we cannot overwrite the old token with the new one on the server side.
Could you please advise:
Is this behavior expected in iOS 26.4 Beta?
How long does it normally take for a device token to become invalid after an app is uninstalled?
What is the recommended approach to prevent duplicate push notifications in this situation?
Any guidance would be greatly appreciated.
Best regards
I am building a simple iOS app that shows the total phone usage time for today using the Screen Time APIs.
Architecture:
Main app
→ requests authorization using AuthorizationCenter.shared.requestAuthorization(for: .individual)
→ displays a DeviceActivityReport
Report extension
→ DeviceActivityReportExtension
→ calculates total usage using DeviceActivityResults<DeviceActivityData>
→ shows the number in a SwiftUI view
The report works correctly. The extension successfully calculates the total usage and displays it on screen.
Example logic inside the report extension:
for await activityData in data {
for await segment in activityData.activitySegments {
totalSeconds += segment.totalActivityDuration
}
}
let totalMinutes = Int(totalSeconds / 60)
The problem:
I need the main app to access that number so I can store it daily in my own database.
I tried to send the value from the extension to the main app using:
App Group + UserDefaults(suiteName:)
App Group + shared file (FileManager.containerURL)
writing inside makeConfiguration(...)
Example:
if let defaults = UserDefaults(suiteName: "group.myapp") {
defaults.set(value, forKey: "savedTotalActivity")
}
But the main app cannot read the value. The report extension displays the number correctly, but the data never appears in shared storage.
Questions:
Is DeviceActivityReportExtension intentionally sandboxed so Screen Time data cannot be exported to the containing app?
Is there any supported way for the main app to access the total usage value calculated in the report extension?
If exporting the value is restricted, what is the recommended architecture for apps that want to store daily Screen Time totals for later analysis?
Goal:
I want a simple app that records something like:
2026-03-08 → 244 minutes
2026-03-09 → 198 minutes
and stores it inside the app database.
Any guidance on the correct architecture would help.
I've run into what appears to be a bug in PDFKit's radio button serialization.
When creating a radio button group with PDFAnnotation, only the first annotation added via page.addAnnotation() gets a correct /AS entry in the written PDF — all other annotations always get /AS /Off, regardless of buttonWidgetState.
Minimal reproduction
func makeRadioButton(optionId: String, isSelected: Bool) -> PDFAnnotation {
let ann = PDFAnnotation(bounds: CGRect(x: 0, y: 0, width: 20, height: 20),
forType: .widget, withProperties: nil)
ann.widgetFieldType = .button
ann.widgetControlType = .radioButtonControl
ann.fieldName = "Choice"
ann.buttonWidgetStateString = optionId
ann.buttonWidgetState = isSelected ? .onState : .offState
return ann
}
let pdf = PDFDocument()
let page = PDFPage()
pdf.insert(page, at: 0)
// Intend to select B
page.addAnnotation(makeRadioButton(optionId: "A", isSelected: false))
page.addAnnotation(makeRadioButton(optionId: "B", isSelected: true))
page.addAnnotation(makeRadioButton(optionId: "C", isSelected: false))
_ = pdf.dataRepresentation()
// Result: /AS is /Off for all three — B is not selected in the PDF
What I observed
Selecting A (first annotation added): /AS /A written correctly works
Selecting B or C: /AS /Off for all buttons
Additionally, dataRepresentation() corrupts the in-memory state as a side effect: buttonWidgetState of the selected annotation is .onState before the call and .offState after.
Root cause
During serialization, dataRepresentation() internally calls setButtonWidgetState:.onState on each annotation in turn to generate appearance streams. This triggers PDFKit's radio-group exclusivity logic, which silently clears all other annotations — so by the time /AS is written, only the first annotation's selection survives.
Workaround
It took a while to track this down, so I'm documenting the workaround here in case it helps others.
Add the annotation that should be selected first via page.addAnnotation():
// Add selected annotation first
page.addAnnotation(makeRadioButton(optionId: "B", isSelected: true))
page.addAnnotation(makeRadioButton(optionId: "A", isSelected: false))
page.addAnnotation(makeRadioButton(optionId: "C", isSelected: false))
Tested on macOS 26.3 / Xcode 26.3. Filed as Feedback FB22167174.
Full code including workaround is here:
radio_bug_swift.txt
Has anyone else hit this? Is there a cleaner method I'm missing?
Our watchOS app is exploring adding audio VOIP calling capability using our in-home platform. We are using LiveCommunicationKit for this and have that all hooked up nicely in a proof of concept implementation.
Our use case is primarily based around supporting end-users through various tasks with assistance from a remotely based expert. We would like for our platform to be able to display visual content on the watch's screen during the call – in other words, we would like to be able to treat this as a video call.
LiveCommunicationKit fully supports all video-related flags on watchOS and doesn't appear to have any different symbol availability versus its iOS version. This high-quality thread (https://developer.apple.com/forums/thread/798090) from a DTS engineer suggests that our use case should be valid (i.e. whiteboarding apps) and that the system's response to an accepted income video call is to dismiss the LCK's incoming call screen and bring the target app to the foreground, allowing it to render its custom content. Unfortunately, on watchOS the system doesn't seem to treat a video call any differently from an audio call, and won't dismiss the system UI once it's answered.
We fully realize that Apple Watch doesn't have a camera for outbound video, doesn't support VideoToolbox or other low-level video convenience libraries for simplified rendering and decoding, etc. That's not what we're worried about (yet). The documentation is at best unclear about whether LCK (or CallKit, for that matter) can hand off calls flagged as video-compatible according to how we think they should, which is passing foreground UI over to the app once the call has been accepted by the user.
Can any Apple people shed some light on this? I recognize we are probably trying to do something not many people have before.
I am testing a consumable in-app purchase in the StoreKit sandbox and I am seeing behavior that does not seem correct on repeat purchase attempts.
Product details
Product ID: album.credit.v2
Type: Consumable
Test environment: iOS device + StoreKit sandbox
Purchase flow triggered from my Flutter app using Apple IAP
What happens
First purchase attempt works
My backend receives the confirmation
The album is granted correctly
On the second purchase attempt of the same consumable, I do not get a normal new purchase flow
Instead, StoreKit returns the product as restored
My app then cancels the attempt because a restored transaction arrived during checkout
Expected behavior
Because this product is a consumable, each purchase attempt should behave like a new purchase and allow the user to buy it again.
Actual behavior
On the second attempt, the transaction update comes back as restored instead of a new successful consumable purchase.
Relevant logs
First successful purchase:
[ProPurchasePage] ✅ Pay tapped. starting=false iap=true albumProd=album.credit.v2 proProd=pro.monthly
[IAP] update: id=album.credit.v2 status=PurchaseStatus.restored pendingComplete=false err=null
[IAP] expected=album.credit.v2 starting=true appleFlow=true
[ProPurchasePage] album credit success status=PurchaseStatus.restored receiptLen=5334
[AppleIapService] Sending Apple IAP confirmation for albumId=ariie_west_pretty_girl_summer, buyerUid=PYjgu9TMCieCVDLIdTuawY5k4Ay2
[AppleIapService] appleIapConfirm response status: 200
[AppleIapService] appleIapConfirm applied for albumId=ariie_west_pretty_girl_summer buyerUid=PYjgu9TMCieCVDLIdTuawY5k4Ay2
After that, the purchase is written correctly on my side:
"libraryAlbums": [
{
"AlbumId": "ariie_west_pretty_girl_summer",
"paid": true,
"Quantity": 1
}
]
Second and later attempts:
[ProPurchasePage] ✅ Pay tapped. starting=false iap=true albumProd=album.credit.v2 proProd=pro.monthly
[ProPurchasePage] buyConsumable (album.credit.v2) returned: true
[IAP] update: id=album.credit.v2 status=PurchaseStatus.restored pendingComplete=false err=null
[IAP] expected=album.credit.v2 starting=true appleFlow=true
[IAP] restored arrived during album checkout — cancelling attempt
Question
Is this expected StoreKit sandbox behavior for a consumable, or does this suggest:
a StoreKit sandbox issue,
a problem with how the product is configured in App Store Connect,
or a transaction-handling issue in the app/plugin layer?
Also, is there any Apple-recommended handling for repeated consumable purchases when sandbox keeps surfacing a restored status?
Topic:
App & System Services
SubTopic:
StoreKit
Hello,
I’m planning to use MapKit JS for a production web/mobile application and I’m trying to better understand the quota limits and pricing model.
From the documentation, I understand that MapKit JS provides a free daily limit of:
250,000 map views
25,000 service calls
per Apple Developer Program membership.
However, I’m not clear about what exactly happens if these limits are exceeded.
My questions:
If my application exceeds 250,000 map views or 25,000 service calls in a day, what happens?
Will the API simply start returning errors (for example HTTP 429), or will Apple automatically charge for additional usage?
Is there an official pricing model for usage above the free quota, or do we need to contact Apple to request higher limits?
Are these limits strict daily hard limits that should never be exceeded in production?
I’m trying to design the architecture of my application and would like to understand whether we must strictly stay below these limits or whether scaling beyond them is possible.
Thank you.
Nao consigo confirmar que tenho mais de 18 anos. Nenhum cartão de crédito aceita, aparece tente mais tarde e a imagem da CNH também não é enviada aparece erro.
Topic:
App & System Services
SubTopic:
Hardware
Hello,
I’m implementing VoIP calling in an iOS application using PushKit (VoIP pushes) together with CallKit.
The standard call flow works correctly:
Happy scenario
User A initiates a call.
Server sends a VoIP push to User B.
User B’s device receives the push and reports the incoming call using CallKit.
User B answers the call.
However, I would like clarification about non-happy scenarios and when it is acceptable to use VoIP pushes to update or stop a CallKit ringing state.
Apple documentation warns that VoIP pushes must be used only when they result in a call-related action, so I want to ensure the following cases are compliant.
Scenario A — Caller Cancels Before Answer
User A calls User B.
Server sends a VoIP push to User B.
User B’s device starts ringing via CallKit.
Before User B answers, User A cancels the call.
Question:
Is it acceptable to send another VoIP push to User B indicating that the call has been cancelled so the device can:
stop the CallKit ringing UI
end the call
optionally mark it as missed or cancelled
Or should this state change be handled using a regular remote push or another signaling mechanism instead of VoIP push?
Scenario B — Callee Rejects the Call
User B rejects the call from CallKit.
The server must inform User A that the call was rejected.
Question:
Is it acceptable to send a VoIP push to User A to update the CallKit state and terminate the outgoing call UI?
Scenario C — Multiple Devices per User
User B may be logged in on multiple devices.
User A calls User B.
VoIP push is sent to all devices of User B.
One device answers.
Question:
Is it acceptable to send a VoIP push to the remaining devices instructing them to:
stop ringing
end the CallKit incoming call UI
Or is there a recommended alternative pattern for this case?
Main Question
Aside from the initial incoming call VoIP push, in which situations is it considered acceptable to send additional VoIP pushes to terminate or update CallKit state (cancelled, rejected, answered on another device)?
The goal is to remain compliant with PushKit policies, particularly the guidance that VoIP pushes should only be used when they result in a call-related user action.
Any guidance on the recommended architecture for these cases would be greatly appreciated.
Thank you.
Hello DTS team, the request review from StoreKit is not working in iOS 26.4 beta 3. I have filed a feedback (FB22157147).
Sample code:
import SwiftUI
import StoreKit
struct ContentView: View {
@Environment(\.requestReview) private var requestReview
@State private var count = 0
var body: some View {
VStack {
Button("Increase Count") {
count += 1
}
Text(count, format: .number)
.font(.largeTitle)
}
.onChange(of: count) {
if count == 3 {
Task {
try await Task.sleep(for: .seconds(2))
requestReview()
print("Request Review triggered!")
// On iPadOS 26.4 beta 2 & 3, requestReview() does not trigger any review system sheet when testing in Xcode 26.3
// Works on iOS 26.3.1
}
}
}
}
}