Skip to main content

cafebazaar_billing 1.2.0 copy "cafebazaar_billing: ^1.2.0" to clipboard
cafebazaar_billing: ^1.2.0 copied to clipboard

PlatformAndroid

cafebazaar_billing is a Flutter plugin that acts as a gate to Cafe Bazaar's native Android In-App Billing, so Flutter apps can sell products and subscriptions on the Cafe Bazaar store.

cafebazaar_billing #

pub package Flutter Android Dart License

cafebazaar_billing is a Flutter plugin that acts as a gate to Cafe Bazaar's native Android In-App Billing. It lets your Flutter app sell products and subscriptions on the Cafe Bazaar store by bridging your Dart code to the Android-native billing implementation.

This package is an independent project — it is not Poolakey and not a wrapper around any other Flutter package.

Android only — Cafe Bazaar is an Android app store.


Table of Contents #


Features #

Feature Method
Connect / disconnect to Bazaar billing service connect / disconnect
Buy consumable / non-consumable products purchase
Buy subscriptions subscribe
Apply developer dynamic pricing dynamicPriceToken parameter
Attach server-verifiable metadata to orders payload parameter
Consume products so they can be re-purchased consume
List user's purchased products getAllPurchasedProducts
Find a purchased product by id queryPurchasedProduct
List user's subscriptions getAllSubscribedProducts
Find a subscription by id querySubscribedProduct
In-app product details (title, price, …) getInAppSkuDetails
Subscription product details getSubscriptionSkuDetails
Trial-subscription availability checkTrialSubscription

Requirements #

  • Flutter >= 3.3.0, Dart >= 3.0.6
  • Android minSdk 21
  • The Cafe Bazaar app installed on the device
  • An RSA public key from your Pishkhan panel (optional — omit only if you verify purchases server-side through Bazaar's REST API)
  • Products configured in your Pishkhan panel with matching SKUs

Familiarize yourself with the official flow in the Cafe Bazaar developer documentation.

Installation #

From pub.dev (recommended):

flutter pub add cafebazaar_billing

or add it manually to pubspec.yaml:

dependencies:
  cafebazaar_billing: ^1.2.0
Alternative: install from GitHub or a local path

From GitHub:

dependencies:
  cafebazaar_billing:
    git:
      url: https://github.com/mavan-innovative-studio/cafebazaar-billing-package.git
      ref: main

Or as a local path:

dependencies:
  cafebazaar_billing:
    path: ../cafebazaar_billing

Then:

flutter pub get

No extra manifest or Gradle setup is needed — the plugin declares everything required (including the <queries> entry for com.farsitel.bazaar) via its own manifest.

Quick Start #

import 'package:cafebazaar_billing/cafebazaar_billing.dart';

Future<void> buyGems() async {
  // 1. Connect (do this once, e.g. after login).
  await CafeBazaarBilling.connect(
    'YOUR_RSA_PUBLIC_KEY',          // null => skips local signature validation
    onSucceed: () => print('Connected'),
    onFailed: () => print('Connection failed'),
    onDisconnected: () {
      print('Disconnected — reconnect before buying again');
    },
  );

  // 2. Start a purchase. The Bazaar payment screen opens.
  final PurchaseInfo info = await CafeBazaarBilling.purchase(
    'gem_pack_100',
    payload: 'user:42',             // optional, stored with the order
  );

  print('Purchased: ${info.productId}, token: ${info.purchaseToken}');

  // 3. For consumables, consume so the user can buy again.
  await CafeBazaarBilling.consume(info.purchaseToken);

  // 4. Disconnect when you no longer need billing (e.g. in dispose()).
  await CafeBazaarBilling.disconnect();
}

Always wrap billing calls in try/catch; every failure surfaces as a PlatformException.

Full API Reference #

Import:

import 'package:cafebazaar_billing/cafebazaar_billing.dart';

Connection #

connect()

static Future<void> connect(
  String? inAppBillingKey, {
  VoidCallback? onSucceed,
  VoidCallback? onFailed,
  VoidCallback? onDisconnected,
})

Opens the connection to the Bazaar billing service. Call this before any other method.

Parameter Description
inAppBillingKey Your RSA public key from Pishkhan. Pass null to disable local signature checks (only safe if you validate purchases via Bazaar's REST API).
onSucceed Connection established — billing methods are now usable.
onFailed Connection attempt failed.
onDisconnected The service dropped (Bazaar killed/uninstalled…). Reconnect before further calls.

disconnect()

static Future<void> disconnect()

Closes the connection. Call it when leaving a page that does billing (e.g. in dispose()) to avoid leaks.

Purchases & Subscriptions #

purchase()

static Future<PurchaseInfo> purchase(
  String productId, {
  String payload = '',
  String dynamicPriceToken = '',
})

Launches the Bazaar purchase flow for productId. Resolves with the resulting PurchaseInfo; throws a PlatformException if cancelled or failed.

Parameter Description
productId The SKU of the product, exactly as configured in Pishkhan.
payload Optional free-form data (e.g. user:42). Stored with the order; read it back from PurchaseInfo.payload or your backend for verification.
dynamicPriceToken Optional token to apply a developer-defined discount/price change for a specific user. See official docs.

subscribe()

static Future<PurchaseInfo> subscribe(
  String productId, {
  String payload = '',
  String dynamicPriceToken = '',
})

Same contract as purchase(), but for subscription SKUs.

consume()

static Future<bool> consume(String purchaseToken)

Consumes a product using PurchaseInfo.purchaseToken, allowing it to be bought again. Only call this for consumable items (gems, coins…). Never consume permanent unlocks or subscriptions.

Inventory Queries #

static Future<List<PurchaseInfo>> getAllPurchasedProducts()
static Future<PurchaseInfo?> queryPurchasedProduct(String productId)
static Future<List<PurchaseInfo>> getAllSubscribedProducts()
static Future<PurchaseInfo?> querySubscribedProduct(String productId)
  • getAll* return the user's full inventory of purchases/subscriptions.
  • query* are convenience lookups returning null when the user does not own the product.

Typical use — restore purchases at app start:

final owned = await CafeBazaarBilling.queryPurchasedProduct('remove_ads');
if (owned != null && owned.purchaseState == PurchaseState.PURCHASED) {
  unlockProFeatures();
}

Product Details (SKU) #

static Future<List<SkuDetails>> getInAppSkuDetails(List<String> skuIds)
static Future<List<SkuDetails>> getSubscriptionSkuDetails(List<String> skuIds)

Returns localized titles/prices/descriptions for rendering your own store UI:

final details = await CafeBazaarBilling.getInAppSkuDetails(['gem_pack_100']);
print(details.first.price); // "۱۰۰٬۰۰۰ ریال"

Trial Subscription #

static Future<Map> checkTrialSubscription()

Checks whether the user is still eligible for a free trial:

final trial = await CafeBazaarBilling.checkTrialSubscription();
print(trial['isAvailable']);      // bool
print(trial['trialPeriodDays']);  // int

Version #

static Future<String> getVersion()

Returns the underlying native billing library version — useful for support tickets and debugging.

Data Models #

PurchaseInfo #

Returned by every purchase/query method.

Field Type Description
orderId String Unique order id assigned by Bazaar.
purchaseToken String Token identifying the purchase — pass to consume() or your backend verification.
payload String The payload you attached when purchasing.
packageName String Your application id.
purchaseState PurchaseState PURCHASED or REFUNDED.
purchaseTime int Purchase timestamp (epoch millis).
productId String The SKU that was bought.
originalJson String Raw JSON from the store — useful for server-side verification.
dataSignature String RSA signature of originalJson (empty when local security check is disabled).

SkuDetails #

Returned by SKU-detail queries.

Field Type Description
sku String Product id.
type String Product type (inapp or subscription).
price String Localized price string, ready to display.
title String Localized product title.
description String Localized description.

PurchaseState #

enum PurchaseState { PURCHASED, REFUNDED }

Error Handling #

All errors are thrown as PlatformException — branch on e.code:

Code Meaning Suggested action
PAYMENT_CONNECTION_IS_NOT_CONNECTED Billing service not connected yet (or dropped). Call connect() and retry once connected.
PURCHASE_FAILED Generic failure while starting/finishing a purchase. Log & show a retry dialog.
PURCHASE_CANCELLED User backed out of the Bazaar screen. Silent or gentle toast — not an error state.
FAILED_TO_BEGIN_FLOW Bazaar could not launch the payment flow. Check that Bazaar is installed & updated.
CONSUME_FAILED Consumption rejected (already consumed / not owned). Refresh inventory before retrying.
QUERY_PURCHASED_PRODUCT_FAILED / QUERY_SUBSCRIBED_PRODUCT_FAILED Inventory query failed. Retry after reconnecting.
QUERY_GET_IN_APP_SKU_DETAILS_FAILED / QUERY_GET_SUBSCRIPTION_SKU_DETAILS_FAILED SKU lookup failed. Verify the SKUs exist in Pishkhan.
CHECK_TRIAL_FAILED Trial eligibility check failed. Treat as "no trial info".
try {
  await CafeBazaarBilling.consume(token);
} on PlatformException catch (e) {
  switch (e.code) {
    case 'PURCHASE_CANCELLED':
      break;                       // user changed their mind
    case 'PAYMENT_CONNECTION_IS_NOT_CONNECTED':
      await reconnect();
    default:
      showError(e.message);
  }
}

Example App #

A complete, ready-to-run demo lives in example/ featuring:

  • Live connection status indicator
  • Configurable RSA key + connect/disconnect controls
  • Sample product catalog with buy & subscribe actions
  • Real-time inventory view with one-tap consume
  • Trial-subscription check and version display
  • An activity log console showing every event and error code
cd example
flutter pub get
flutter run

A device (or emulator) with the Cafe Bazaar app installed is required for real flows.

Troubleshooting & FAQ #

PAYMENT_CONNECTION_IS_NOT_CONNECTED right after calling purchase Wait for onSucceed before enabling buy buttons; reconnect on onDisconnected.

Connection fails immediately Cafe Bazaar must be installed and signed-in on the device. Emulators without Play services need the Bazaar APK sideloaded.

Signature verification fails (dataSignature issues) Make sure the RSA key passed to connect() matches the key of the upload certificate used to sign the app, and that you didn't intend to pass null.

Purchases disappear after reinstall They don't — restore them with getAllPurchasedProducts() / getAllSubscribedProducts() at startup.

Does it work on iOS / web / desktop? No. Cafe Bazaar billing is Android-only; calls on other platforms throw MissingPluginException.

Can I verify purchases on my server? Yes. Send orderId, purchaseToken and originalJson to your backend and validate through Bazaar's REST API; keep connect(null) only if you rely solely on server-side validation.

License #

Distributed under a custom license: free to use, modify and distribute, but provided "as is" — without any warranty, and the author accepts no liability whatsoever for any damage, malfunction or side effects.

2
likes
150
points
142
downloads

Documentation

API reference

Publisher

unverified uploader

Weekly Downloads

cafebazaar_billing is a Flutter plugin that acts as a gate to Cafe Bazaar's native Android In-App Billing, so Flutter apps can sell products and subscriptions on the Cafe Bazaar store.

Homepage
Repository (GitHub)
View/report issues

License

MIT (license)

Dependencies

flutter, plugin_platform_interface

More

Packages that depend on cafebazaar_billing

Packages that implement cafebazaar_billing