Allega un appAccountToken a ogni acquisto sull'App Store, oppure non potrai difendere il rimborso
Apple invia al tuo server un CONSUMPTION_REQUEST quando un cliente chiede un rimborso, ma la transazione non dice mai chi sia. appAccountToken è l'UUID che collega un acquisto al tuo utente. Impostalo e potrai rispondere ad Apple con dati reali. Salta questo passaggio e stai tirando a indovinare.

Punti chiave
- appAccountToken è un UUID che alleghi a un acquisto sull'App Store affinché la transazione risultante punti all'utente esatto nel tuo sistema. Apple lo memorizza sulla transazione e lo restituisce ovunque quella transazione compaia.
- L'unica regola di formato che Apple impone è che il valore sia un UUID valido. Passa qualsiasi altra cosa, un id, un'e-mail, una stringa concatenata, e StoreKit lo scarta silenziosamente e restituisce appAccountToken come nil.
- In StoreKit 2 lo imposti con una sola opzione d'acquisto, Product.PurchaseOption.appAccountToken(_:), usando un UUID stabile che hai generato e memorizzato per quell'account.
- Impostalo una volta sull'acquisto originale e Apple mantiene lo stesso token attraverso ogni rinnovo, nuovo tentativo di addebito e upgrade della catena di abbonamento.
- Dal 2025, l'endpoint Set App Account Token permette al tuo server di allegare un token agli acquisti effettuati fuori dalla tua app, come i riscatti di codici promozionali e gli acquisti promossi, che il flusso interno all'app non poteva mai raggiungere.
- appAccountToken è ciò che rende il CONSUMPTION_REQUEST di Apple a cui puoi rispondere. Senza di esso non puoi collegare il rimborso al cliente il cui utilizzo devi descrivere entro la finestra di 12 ore.
- Un rimborso che non puoi identificare è un rimborso che non puoi difendere. Restituisci denaro su acquisti che avevi le prove per trattenere, oltre al calcolo, alle chiamate API e ai pagamenti che hai già speso per consegnarli.
Un cliente chiede un rimborso ad Apple, Apple invia al tuo server un CONSUMPTION_REQUEST, e hai dodici ore per rispondere con dati reali su come quella persona ha usato il prodotto. Poi apri la notifica e ti rendi conto di non avere idea di chi sia. La transazione porta un originalTransactionId e un id di prodotto, ma nulla che punti all'account nel tuo database. Questo divario è esattamente ciò che appAccountToken colma, e se non lo hai impostato al momento dell'acquisto, non puoi colmarlo a posteriori per quella vendita.
appAccountToken è un UUID che alleghi a un acquisto affinché la transazione risultante dell'App Store porti un puntatore all'utente esatto nel tuo sistema. Impostalo, e ogni domanda di rimborso che Apple porrà mai su quel cliente arriverà con la sua identità allegata. Salta questo passaggio, e stai tirando a indovinare. Ecco cos'è questo campo, come impostarlo, il nuovo endpoint che salva gli acquisti effettuati fuori dalla tua app, e quanto costa davvero il collegamento mancante quando arriva un rimborso.
Cos'è davvero appAccountToken
appAccountToken è un UUID opaco che generi e passi a StoreKit al momento dell'acquisto. Apple lo memorizza sulla transazione e lo restituisce nelle informazioni della transazione di quell'acquisto, e lì rimane. Nelle parole di Apple, è "l'UUID che associa la transazione all'account dell'utente sul tuo servizio". L'unica regola di formato è che deve essere un UUID. Apple non lo legge, non convalida a cosa punti, e non le importa cosa significhi dalla tua parte. È un collegamento che controlli tu.
Poiché vive sulla transazione, torna ovunque vada la transazione. La transazione firmata in una notifica del server, la risposta Get Transaction Info dell'App Store Server API, e ogni rinnovo di una catena di abbonamento portano tutti lo stesso token se lo hai impostato sull'acquisto originale. Un UUID, allegato una volta, segue la fatturazione del cliente per l'intera durata del rapporto.
Deve essere un UUID vero, altrimenti scompare silenziosamente
L'unica regola che Apple impone è il formato. StoreKit 2 richiede un UUID RFC 4122. Se passi una stringa concatenata, un id intero o un indirizzo e-mail, StoreKit non solleva errori. Scarta il valore e la transazione torna con appAccountToken a nil. Gli sviluppatori ci sbattono contro di continuo, e il sintomo è sempre lo stesso, qualche variante di "appAccountToken is missing in the transaction payload" sugli stessi forum di Apple, quasi sempre perché il valore passato non era un UUID valido. Genera un UUID vero lato server, memorizzalo associato all'account, e non passare mai altro a StoreKit.
Come impostarlo al momento dell'acquisto
In StoreKit 2 è una singola opzione d'acquisto. Genera l'UUID sul tuo server quando l'utente si registra o arriva per la prima volta al checkout, memorizzalo nel record del suo account, e passa quello stesso valore alla chiamata d'acquisto.
La firma è Product.PurchaseOption.appAccountToken(_ token: UUID), e un acquisto ha questo aspetto try await product.purchase(options: [.appAccountToken(token)]). Quando la transazione torna, verificata tramite l'App Store Server API o consegnata da una notifica del server, porta quell'UUID, e il tuo server trova il cliente in una sola query.
Usa un token stabile per account
Non generare un token nuovo per ogni acquisto dello stesso utente. Apple restituisce il token sui rinnovi, sui nuovi tentativi di addebito e sugli upgrade della stessa catena, quindi un UUID stabile per account ti dà un filo pulito dal primo acquisto attraverso ogni evento futuro. Un token che cambia a ogni acquisto spezza quel filo e vanifica l'intero scopo. Un account, un token, riutilizzato ogni volta che quell'account acquista.
L'endpoint che salva gli acquisti fuori dall'app
Fino al 2025 c'era un buco. Se un cliente riscattava un codice promozionale o effettuava un acquisto in-app promosso direttamente dall'App Store, la tua app non eseguiva mai il flusso d'acquisto, quindi non c'era nessun posto dove impostare appAccountToken. Quelle transazioni arrivavano anonime e tali restavano.
La WWDC 2025 ha colmato il divario con l'endpoint Set App Account Token. Il tuo server chiama PUT /inApps/v1/transactions/{originalTransactionId}/appAccountToken sull'App Store Server API con l'UUID nel corpo, e Apple imposta il token su quella transazione. Funziona per ogni tipo di prodotto, copre i riscatti di codici promozionali e gli acquisti promossi, e il valore che invii sovrascrive qualsiasi token già presente sulla transazione. Ora puoi associare un acquisto a posteriori, dal tuo server, senza che passi mai per la tua app.

| Canale d'acquisto | Dove imposti appAccountToken | Note |
|---|---|---|
| Acquisto in-app | Opzione d'acquisto StoreKit al momento dell'acquisto | Product.PurchaseOption.appAccountToken(UUID) |
| Riscatto di codice promozionale | Endpoint Set App Account Token, lato server | Nessun flusso in-app a cui agganciarsi, quindi impostalo dopo |
| Acquisto in-app promosso dall'App Store | Endpoint Set App Account Token, lato server | L'acquisto avviene fuori dalla tua app |
| Rinnovo di abbonamento | Niente da fare | Ereditato automaticamente dall'acquisto originale |
Dove il collegamento mancante ti costa denaro
Lo scopo del token non sono registri ordinati. È che l'unica domanda di rimborso che Apple pone agli sviluppatori, il CONSUMPTION_REQUEST, ha una risposta solo se riesci a trovare il cliente a cui si riferisce.
Quando un acquirente richiede un rimborso su un consumabile o un abbonamento non rinnovabile, Apple invia al tuo server una notifica CONSUMPTION_REQUEST e ti dà dodici ore per rispondere con Send Consumption Information. La tua risposta sono dati su quel cliente specifico: quanto del prodotto ha consumato, l'anzianità del suo account, la sua spesa complessiva, il suo stato di consegna. appAccountToken è esso stesso uno dei campi di quella richiesta, e ancora più importante, è il modo in cui la transazione della notifica corrisponde all'account il cui utilizzo stai per descrivere. Nessun token, nessuna ricerca, nessuna risposta accurata.
Quanto costa davvero una risposta vuota
Un rimborso non identificato costringe a una cattiva scelta. Puoi rispondere alla richiesta di consumo con niente, il che viene letto come basso consumo e spinge Apple verso la concessione del rimborso, anche a clienti che hanno usato il prodotto in modo intensivo. Oppure puoi tirare a indovinare. In entrambi i casi stai rimborsando acquisti che avevi le prove per difendere, e hai già pagato il costo reale di servirli.
Quel costo non è il prezzo di vendita. Un consumabile che ha eseguito un lotto di chiamate all'API di un modello, generato immagini, esportato un video o attivato un pagamento a un creator ha speso denaro reale nel momento in cui è stato consegnato. Il rimborso restituisce il pagamento del cliente. Non restituisce la fattura del fornitore. Moltiplica un cliente non identificabile per ogni rimborso che apre, e per ogni rimborsatore seriale che conta sul fatto che tu non sappia chi sia, e il token che hai saltato diventa la riga di codice più costosa che non hai mai scritto.
La stessa idea esiste su Android, con un altro nome
Google Play risolve il problema identico con setObfuscatedAccountId, che allega un identificatore di account a un acquisto affinché la revisione dei chargeback di Google tramite orders.reviewrefund possa avere una risposta a fronte di un utente reale. Store diverso, meccanica diversa, la stessa lezione: allega l'identità al momento dell'acquisto o non potrai difendere la contestazione in seguito. Sull'App Store, quello strumento è appAccountToken, e deve essere un UUID.
Tre abitudini che tengono il token al suo posto
- Genera un UUID per account e memorizzalo. Un token stabile per cliente, creato quando si registra o al primo checkout, salvato nel suo record e riutilizzato per ogni acquisto.
- Convalidalo prima di passarlo. Conferma che il valore sia un UUID vero nel tuo codice d'acquisto, così un id malformato non potrà mai diventare silenziosamente un token nil sulla transazione.
- Completa gli acquisti fuori dall'app. Quando arriva una notifica del server per un riscatto di codice promozionale o un acquisto promosso senza token, chiama l'endpoint Set App Account Token per allegare quello giusto.
Fai queste tre cose e ogni transazione che Apple ti invierà, richieste di rimborso comprese, arriverà già legata al cliente a cui appartiene.
Questa è la base su cui RefundHalt fa affidamento. Leggiamo appAccountToken da ogni transazione e notifica del server, lo colleghiamo all'utilizzo che già tracciamo per quell'account, e rispondiamo alla richiesta di consumo di Apple entro la finestra di dodici ore con i numeri reali del cliente. Il token è il filo. Impostalo una volta e la tua difesa dai rimborsi avrà qualcosa a cui aggrapparsi.
Domande frequenti
- Cos'è appAccountToken nell'App Store?
- appAccountToken è un UUID che generi e alleghi a un acquisto tramite StoreKit affinché la transazione risultante dell'App Store punti a un account utente specifico nel tuo sistema. Apple lo memorizza sulla transazione e lo restituisce nelle informazioni della transazione, nelle notifiche del server e in ogni rinnovo della stessa catena, il che ti permette di collegare qualsiasi evento futuro, inclusa una richiesta di rimborso, al cliente giusto.
- Perché il mio appAccountToken è nil o mancante?
- Quasi sempre perché il valore che hai passato non era un UUID valido. StoreKit 2 richiede un UUID RFC 4122 e scarta silenziosamente qualsiasi altra cosa, quindi una stringa concatenata, un id intero o un'e-mail tornano come un appAccountToken nil mentre l'acquisto va comunque a buon fine. L'altra causa comune è un acquisto effettuato fuori dalla tua app, come un riscatto di codice promozionale, dove non è stato eseguito alcun flusso in-app per impostare il token.
- Posso impostare appAccountToken dopo l'acquisto, per i codici promozionali?
- Sì, dal 2025. L'endpoint Set App Account Token dell'App Store Server API permette al tuo server di allegare o sovrascrivere il token su una transazione esistente chiamando PUT /inApps/v1/transactions/{originalTransactionId}/appAccountToken con l'UUID nel corpo. Funziona per ogni tipo di prodotto ed è pensato per gli acquisti effettuati fuori dalla tua app, come i riscatti di codici promozionali e gli acquisti in-app promossi.
- appAccountToken deve essere un UUID?
- Sì. L'unica regola di formato che Apple impone è che il valore sia un UUID valido. Per il resto è opaco, quindi può corrispondere alla chiave di account che preferisci dalla tua parte, ma se non è un UUID StoreKit non lo memorizzerà e la transazione tornerà con appAccountToken a nil.
- Come aiuta appAccountToken con i rimborsi?
- Quando un cliente richiede un rimborso, Apple invia un CONSUMPTION_REQUEST e ti dà dodici ore per rispondere con dati su quello specifico acquirente. appAccountToken è il modo in cui fai corrispondere la transazione della notifica all'account il cui utilizzo devi riportare, ed è uno dei campi della richiesta di consumo stessa. Senza di esso non puoi rispondere con l'utilizzo reale, quindi Apple tende a concedere rimborsi che avevi le prove per contestare.
- appAccountToken dovrebbe essere diverso per ogni acquisto?
- No. Usa un unico UUID stabile per account e riutilizzalo per ogni acquisto che quell'utente effettua. Apple mantiene il token attraverso i rinnovi e gli upgrade di una catena di abbonamento, quindi un token stabile ti dà un collegamento pulito nel tempo. Un token che cambia a ogni acquisto spezza quel collegamento e rende più difficile ricondurre le transazioni allo stesso cliente.
Fonti e approfondimenti
- Apple Developer: appAccountToken (StoreKit Transaction)
- Apple Developer: Product.PurchaseOption.appAccountToken(_:)
- Apple Developer: Set App Account Token (App Store Server API)
- Apple Developer: appAccountToken (App Store Server API)
- Apple Developer: ConsumptionRequest (Send Consumption Information)
- Apple Developer: Send Consumption Information
- WWDC25: Dive into App Store server APIs for In-App Purchase
RefundHalt
Il pilota automatico dei rimborsi per App Store e Google Play
Continua a leggere
Non confermi un acquisto Google Play entro tre giorni e Google lo rimborsa, ecco cosa ti costa
Google Play rimborsa e revoca automaticamente qualsiasi acquisto che il tuo server non conferma entro tre giorni. È un errore di integrazione, non una decisione del cliente, ed è del tutto evitabile. Ecco la regola esatta, perché scatta e quanto costa davvero ogni vendita persa.
L'abuso ripetuto dei rimborsi ti costa due volte, ecco come gli store ti lasciano reagire
Il cliente che si fa rimborsare più e più volte non è un caso. L'abuso dei rimborsi ti costa il denaro restituito più il calcolo che hai già speso, ed entrambi gli store ti forniscono un segnale di identità, l'appAccountToken di Apple e l'ID account offuscato di Google, per collegare lo schema.