Skip to content
This repository was archived by the owner on Feb 22, 2023. It is now read-only.

[in_app_purchase] Added currency code and numerical price to product detail model. #3794

Merged
merged 12 commits into from
Apr 9, 2021
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions packages/in_app_purchase/in_app_purchase/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
## 0.5.2

* Added `rawPrice` and `currencyCode` to the ProductDetails model.

## 0.5.1+2

* Update README to provide a better instruction of the plugin.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ class ProductDetails {
required this.title,
required this.description,
required this.price,
required this.rawPrice,
required this.currencyCode,
this.skProduct,
this.skuDetail});

Expand All @@ -33,6 +35,13 @@ class ProductDetails {
/// Formatted with currency symbol ("$0.99").
final String price;

/// The unformatted price of the product, specified in the App Store Connect or Sku in Google Play console based on the platform.
final double rawPrice;

/// The currency code for the price of the product.
/// Based on the price specified in the App Store Connect or Sku in Google Play console based on the platform.
final String currencyCode;

/// Points back to the `StoreKits`'s [SKProductWrapper] object that generated this [ProductDetails] object.
///
/// This is `null` on Android.
Expand All @@ -49,6 +58,8 @@ class ProductDetails {
this.title = product.localizedTitle,
this.description = product.localizedDescription,
this.price = product.priceLocale.currencySymbol + product.price,
this.rawPrice = double.parse(product.price),
this.currencyCode = product.priceLocale.currencyCode,
this.skProduct = product,
this.skuDetail = null;

Expand All @@ -58,6 +69,8 @@ class ProductDetails {
this.title = skuDetails.title,
this.description = skuDetails.description,
this.price = skuDetails.price,
this.rawPrice = ((skuDetails.priceAmountMicros) / 1000000.0).toDouble(),
this.currencyCode = skuDetails.priceCurrencyCode,
this.skProduct = null,
this.skuDetail = skuDetails;
}
Expand Down
2 changes: 1 addition & 1 deletion packages/in_app_purchase/in_app_purchase/pubspec.yaml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
name: in_app_purchase
description: A Flutter plugin for in-app purchases. Exposes APIs for making in-app purchases through the App Store and Google Play.
homepage: https://github.com/flutter/plugins/tree/master/packages/in_app_purchase
version: 0.5.1+2
version: 0.5.2

dependencies:
flutter:
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

import 'package:flutter_test/flutter_test.dart';
import 'package:in_app_purchase/in_app_purchase.dart';
import 'package:in_app_purchase/src/store_kit_wrappers/sk_product_wrapper.dart';

void main() {
group('Constructor Tests', () {
test('fromSkProduct should correctly parse the price data', () {
final SKProductWrapper dummyProductWrapper = SKProductWrapper(
productIdentifier: 'id',
localizedTitle: 'title',
localizedDescription: 'description',
priceLocale:
SKPriceLocaleWrapper(currencySymbol: '\$', currencyCode: 'USD'),
subscriptionGroupIdentifier: 'com.group',
price: '13.37',
);

ProductDetails productDetails =
ProductDetails.fromSKProduct(dummyProductWrapper);
expect(productDetails.rawPrice, equals(13.37));
});

test('fromSkuDetails should correctly parse the price data', () {
final SkuDetailsWrapper dummyDetailWrapper = SkuDetailsWrapper(
description: 'description',
freeTrialPeriod: 'freeTrialPeriod',
introductoryPrice: 'introductoryPrice',
introductoryPriceMicros: 'introductoryPriceMicros',
introductoryPriceCycles: 1,
introductoryPricePeriod: 'introductoryPricePeriod',
price: '13.37',
priceAmountMicros: 13370000,
priceCurrencyCode: 'usd',
sku: 'sku',
subscriptionPeriod: 'subscriptionPeriod',
title: 'title',
type: SkuType.inapp,
originalPrice: 'originalPrice',
originalPriceAmountMicros: 1000,
);

ProductDetails productDetails =
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we should also test productDetails.currencyCode

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The main reason I only decided to test the rawPrice property is because it is the only one that has some additional logic in the constructors (String parsing for iOS, some math for Android).

I can of course also test currencyCode, but since that's nothing more than a value being set, just like all the other pre-existing properties, it does make me wonder if those should then also be tested (e.g. title, description, etc).

I'm curious if you have any thoughts on this?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it does make me wonder if those should then also be tested (e.g. title, description, etc).

Ideally, if we can, it would be nice to test all the properties being set with the constructor. It would be awesome if you could add those in this PR!

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure thing! The changes have been added.

ProductDetails.fromSkuDetails(dummyDetailWrapper);
expect(productDetails.rawPrice, equals(13.37));
});
});
}