← Todas as extensões

Extensão nativa

KlugBilling

com.klug.billing

NÃO É NECESSÁRIO APM. Baixe e aproveite. Não tem como ser mais simples. Basta atualizar o Adobe AIR SDK. Se precisar de ajuda, estamos aqui.

Compras no app e assinaturas para apps AIR na App Store e no Google Play, com uma única API ActionScript para as duas lojas.

iOS Android Em produção A partir de €19 / ano · Comprar

Visão geral

O KlugBilling vende produtos de compra única e assinaturas a partir do seu app AIR. No iPhone e iPad ele se comunica com a App Store, no Android com o Google Play, e o seu código ActionScript continua o mesmo para os dois.

Ele carrega os seus produtos com títulos e preços localizados, abre a tela de compra da loja, informa cada etapa de uma transação e a finaliza depois que você entrega o produto. A restauração de compras anteriores, o recibo do app iOS e os dados de compra assinados do Google Play estão incluídos, para que o seu servidor possa verificar cada venda.

No Android, o KlugBilling usa a versão atual da Google Play Billing Library 8. Ela é adicionada automaticamente quando o app é empacotado e atende aos requisitos do Google Play para novos apps e atualizações.

O KlugBilling vende as assinaturas de nossos apps no iOS e Android, nossa prova de conceito.

Recursos

  • Autossuficiente: uma ANE, sem biblioteca principal nem ANEs de dependência para adicionar
  • Uma única API para a App Store e o Google Play
  • Produtos de compra única e assinaturas com renovação automática
  • Títulos, descrições e preços localizados direto da loja
  • Períodos de assinatura, ofertas e fases de preço
  • Cada estado da transação como evento: comprando, comprado, falhou, cancelado, restaurado, adiado
  • Restaurar compras (iOS) e listar as compras existentes (Android)
  • Dados para verificações no servidor: o recibo do app iOS, os dados de compra assinados do Google e a assinatura
  • Android: as compras são verificadas com a sua chave pública do Play

Plataformas compatíveis

iOS iPhone · iPad · App Store
Android celulares · tablets · dobráveis · Google Play Billing Library 8

Em outras plataformas, InAppBilling.isSupported retorna false, de modo que o mesmo código pode permanecer em um app multiplataforma.

Primeiros passos

Adicione a extensão ao descritor do seu aplicativo:

app.xml
<extensions>
    <extensionID>com.klug.billing</extensionID>
</extensions>

Não são necessárias entradas no manifesto nem activities. Crie seus produtos no App Store Connect e no Google Play Console com os mesmos IDs de produto e copie a chave pública base64 do seu app no Play Console (Configuração de monetização).

Exemplos de código

Quatro fluxos completos, extraídos da API que roda em nossos apps. Cada chamada retorna imediatamente; os resultados chegam como eventos em InAppBilling.service. Documentação completa →

1 · Conectar à loja
Store.as
import com.klug.billing.*;
import com.klug.billing.events.*;

var store:InAppBillingService = InAppBilling.service;

if ( InAppBilling.isSupported )   // iOS, Android
{
    store.addEventListener( InAppBillingEvent.SETUP_SUCCESS, onSetup );
    store.addEventListener( InAppBillingEvent.SETUP_FAILURE, onSetupFailed );
    store.addEventListener( PurchaseEvent.PURCHASES_UPDATED, onPurchasesUpdated );   // see 3

    var service:BillingService = new BillingService();
    if ( store.platform == "android" )
        service.setServiceType( InAppBillingServiceTypes.GOOGLE_PLAY_INAPP_BILLING )
               .setGooglePlayPublicKey( "MIIBIjANBgkqh..." );   // from the Play Console, Android only
    else
        service.setServiceType( InAppBillingServiceTypes.APPLE_INAPP_PURCHASE );
    store.setup( service );
}

function onSetup( e:InAppBillingEvent ):void
{
    store.checkAvailability( function( result:String ):void {
        if ( result == InAppBillingAvailability.AVAILABLE ) loadProducts();   // see 2
        else hideShop();   // e.g. purchases disabled by Screen Time
    });
}
2 · Mostrar produtos com preços localizados
Products.as
function loadProducts():void
{
    store.addEventListener( ProductEvent.PRODUCTS_LOADED, onProducts );
    store.addEventListener( ProductEvent.PRODUCTS_FAILED, function( e:ProductEvent ):void {
        trace( "store not reachable: " + e.message );
    });
    // one-time products first, subscriptions second
    store.getProducts( [ "com.example.removeads" ],
                       [ "com.example.pro.monthly", "com.example.pro.yearly" ] );
}

function onProducts( e:ProductEvent ):void
{
    for each ( var p:Product in e.products )
    {
        // e.g. "Pro Yearly · 19,99 €" in the user's currency and language
        addShopButton( p.id, p.title + " · " + p.priceString );   // your app function
    }
}
3 · Comprar, entregar, finalizar
Purchase.as
function buy( productId:String ):void
{
    var request:PurchaseRequest = new PurchaseRequest().setProductId( productId );
    if ( store.checkPurchaseRequestValid( request ) ) store.makePurchase( request );
}

// every step of every transaction, also open ones from earlier sessions
function onPurchasesUpdated( e:PurchaseEvent ):void
{
    for each ( var p:Purchase in e.data )
    {
        switch ( p.transactionState )
        {
            case Purchase.STATE_PURCHASED:
            case Purchase.STATE_RESTORED:
                // iOS: p.transactionReceipt (app receipt)
                // Android: p.originalMessage + p.signature (Google's signed purchase data)
                verifyOnServer( p, function():void {   // your server call
                    unlock( p.productId );              // your app function
                    store.finishPurchase( p );          // close it, or the store sends it again
                });
                break;
            case Purchase.STATE_FAILED:
            case Purchase.STATE_CANCELLED:
                store.finishPurchase( p );
                break;
            case Purchase.STATE_DEFERRED:
                showHint( "Waiting for approval" );   // e.g. Ask to Buy
                break;
        }
    }
}
4 · Restaurar compras anteriores
Restore.as
function restore():void
{
    if ( store.isGetPurchasesSupported )   // Android: list what the Google account owns
    {
        store.addEventListener( PurchaseEvent.GET_PURCHASES_COMPLETE, function( e:PurchaseEvent ):void {
            for each ( var p:Purchase in e.data ) unlock( p.productId );
        });
        store.getPurchases();
    }
    else   // iOS: restored transactions arrive in onPurchasesUpdated with STATE_RESTORED
    {
        store.addEventListener( PurchaseEvent.RESTORE_PURCHASES_SUCCESS, function( e:PurchaseEvent ):void {
            showHint( "Purchases restored" );
        });
        store.restorePurchases();
    }
}

Visão geral da API

InAppBilling.isSupportedVerdadeiro no iOS e Android, falso nas demais plataformas.
InAppBilling.serviceO serviço único da loja; todas as chamadas e eventos abaixo.
setup(service)Conecta-se à loja descrita por um BillingService. Resultado: SETUP_SUCCESS ou SETUP_FAILURE.
checkAvailability(callback)AVAILABLE, NOT_AVAILABLE ou STORE_UPGRADE_REQUIRED.
canMakePaymentsFalso quando as compras estão desativadas no dispositivo.
getProducts(productIds, subscriptionIds)Carrega os dados da loja. Resultado: PRODUCTS_LOADED, INVALID_PRODUCT ou PRODUCTS_FAILED.
getProduct(id)Um Product carregado: title, description, price, priceString, currencyCode, subscriptionPeriod, subscriptionOffers.
makePurchase(request)Abre a tela de compra da loja para um PurchaseRequest; oferta de assinatura opcional.
finishPurchase(purchase)Finaliza uma transação após a entrega. Resultado: FINISH_SUCCESS ou FINISH_FAILED.
getPendingPurchases()Transações que a loja ainda mantém abertas.
restorePurchases()iOS: restaura compras anteriores do Apple ID.
getPurchases()Android: lista as compras da conta Google.
applicationReceiptiOS: o recibo do app em base64 para o seu servidor, com refresh().
dispose()Desconecta da loja.

Eventos

InAppBillingEventSETUP_SUCCESS, SETUP_FAILURE, RESTORE_PURCHASES_SUCCESS, RESTORE_PURCHASES_FAILED
ProductEventPRODUCTS_LOADED (produtos), INVALID_PRODUCT, PRODUCTS_FAILED
PurchaseEventPURCHASES_UPDATED (data = objetos Purchase), PURCHASE_FAILED, FINISH_SUCCESS, FINISH_FAILED, RESTORE_PURCHASES_SUCCESS, RESTORE_PURCHASES_FAILED, GET_PURCHASES_COMPLETE, GET_PURCHASES_FAILED
AvailabilityEventCOMPLETE com o resultado da disponibilidade
ApplicationReceiptEventREFRESH_SUCCESS, REFRESH_FAILED

Compre o KlugBilling

Uma licença anual para um app AIR, com todas as atualizações por 12 meses. Após o pagamento, você recebe a extensão, a biblioteca ActionScript e a documentação por e-mail, normalmente em até um dia útil. Licença e termos

Simples
€19 / ano
  • Licença para um app AIR
  • Todas as atualizações por 12 meses
  • Sem suporte
Comprar Simples
Padrão
€149 / ano
  • Licença para um app AIR
  • Todas as atualizações por 12 meses
  • Resposta por e-mail em até 7 dias
Comprar Padrão
Prioritário
€299 / ano
  • Licença para um app AIR
  • Todas as atualizações por 12 meses
  • Resposta por e-mail em até 48 horas
Comprar Prioritário
Os impostos são calculados no checkout pelo Link (Stripe). Você informa o ID do aplicativo do seu app AIR durante o checkout.

Requisitos

AIR SDK51.x (HARMAN)
iOSiOS 13 ou posterior, produtos no App Store Connect
AndroidAndroid 6.0 (API 23) ou posterior, produtos no Google Play Console
Google PlayPlay Billing Library 8.3, adicionada no empacotamento
Servidor (recomendado)Verifica o recibo do app iOS ou os dados de compra assinados do Google