Set in-app product card price meta dynamically (#51170)
* Set product card price currency and suffix dynamically based on endpoint data * Add changefile(s) from automation for the following project(s): woocommerce * Remove unnecessary comment * Update types to match data received from WCCOM after further changes to the API * Apply suggestions from code review Allow for future currencies that might switch the symbol/value order Co-authored-by: Dan Q <dan@danq.me> --------- Co-authored-by: github-actions <github-actions@github.com> Co-authored-by: Dan Q <dan@danq.me>
This commit is contained in:
parent
3b35e22c99
commit
904dfaa2ff
|
@ -2,7 +2,7 @@
|
|||
* External dependencies
|
||||
*/
|
||||
import { Button, Icon } from '@wordpress/components';
|
||||
import { __ } from '@wordpress/i18n';
|
||||
import { __, sprintf } from '@wordpress/i18n';
|
||||
import { useContext } from '@wordpress/element';
|
||||
import { recordEvent } from '@woocommerce/tracks';
|
||||
import { navigateTo, getNewPath } from '@woocommerce/navigation';
|
||||
|
@ -64,8 +64,17 @@ function ProductCardFooter( props: { product: Product } ) {
|
|||
return true;
|
||||
}
|
||||
|
||||
// We hardcode this for now while we only display prices in USD.
|
||||
const currencySymbol = '$';
|
||||
const currencyFormats: { [ key: string ]: string } = {
|
||||
USD: '$%s',
|
||||
AUD: 'A$%s',
|
||||
CAD: 'C$%s',
|
||||
EUR: '€%s',
|
||||
GBP: '£%s',
|
||||
};
|
||||
|
||||
const getCurrencyFormat = ( currencyCode: string ) => {
|
||||
return currencyFormats[ currencyCode ] || '%s';
|
||||
};
|
||||
|
||||
function getPriceLabel(): string {
|
||||
if ( product.price === 0 ) {
|
||||
|
@ -76,7 +85,51 @@ function ProductCardFooter( props: { product: Product } ) {
|
|||
return __( 'Free plan available', 'woocommerce' );
|
||||
}
|
||||
|
||||
return currencySymbol + product.price;
|
||||
return sprintf( getCurrencyFormat( product.currency ), product.price );
|
||||
}
|
||||
|
||||
function getPriceSuffix(): string {
|
||||
// Paid simple products have a billing period of ''.
|
||||
if (
|
||||
product.billingPeriodInterval === 1 ||
|
||||
product.billingPeriod === ''
|
||||
) {
|
||||
switch ( product.billingPeriod ) {
|
||||
case 'day':
|
||||
return __( 'daily', 'woocommerce' );
|
||||
case 'week':
|
||||
return __( 'weekly', 'woocommerce' );
|
||||
case 'month':
|
||||
return __( 'monthly', 'woocommerce' );
|
||||
case 'year':
|
||||
case '':
|
||||
return __( 'annually', 'woocommerce' );
|
||||
default:
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
let period;
|
||||
switch ( product.billingPeriod ) {
|
||||
case 'day':
|
||||
period = __( 'days', 'woocommerce' );
|
||||
break;
|
||||
case 'week':
|
||||
period = __( 'weeks', 'woocommerce' );
|
||||
break;
|
||||
case 'month':
|
||||
period = __( 'months', 'woocommerce' );
|
||||
break;
|
||||
default:
|
||||
period = __( 'years', 'woocommerce' );
|
||||
}
|
||||
|
||||
return sprintf(
|
||||
// translators: %1$d: billing period interval, %2$s: billing period (e.g. days, weeks, months, years)
|
||||
__( 'every %1$d %2$s', 'woocommerce' ),
|
||||
product.billingPeriodInterval,
|
||||
period
|
||||
);
|
||||
}
|
||||
|
||||
function getBillingText(): string {
|
||||
|
@ -85,7 +138,7 @@ function ProductCardFooter( props: { product: Product } ) {
|
|||
}
|
||||
|
||||
if ( product.price !== 0 ) {
|
||||
return __( ' annually', 'woocommerce' );
|
||||
return getPriceSuffix();
|
||||
}
|
||||
|
||||
return '';
|
||||
|
|
|
@ -47,6 +47,9 @@ function ProductCard( props: ProductCardProps ): JSX.Element {
|
|||
featuredImage: '',
|
||||
color: '',
|
||||
productCategory: '',
|
||||
billingPeriod: '',
|
||||
billingPeriodInterval: 0,
|
||||
currency: '',
|
||||
};
|
||||
|
||||
function isSponsored(): boolean {
|
||||
|
|
|
@ -105,6 +105,10 @@ export default function ProductListContent( props: {
|
|||
color: product.color,
|
||||
featuredImage: product.featuredImage,
|
||||
productCategory: product.productCategory,
|
||||
billingPeriod: product.billingPeriod,
|
||||
billingPeriodInterval:
|
||||
product.billingPeriodInterval,
|
||||
currency: product.currency,
|
||||
} }
|
||||
tracksData={ {
|
||||
position: index + 1,
|
||||
|
|
|
@ -24,6 +24,9 @@ export type SearchAPIProductType = {
|
|||
featured_image: string;
|
||||
product_category: string;
|
||||
color: string;
|
||||
billing_period: string;
|
||||
billing_period_interval: number;
|
||||
currency: string;
|
||||
};
|
||||
|
||||
export interface Product {
|
||||
|
@ -52,6 +55,9 @@ export interface Product {
|
|||
featuredImage?: string;
|
||||
productCategory?: string;
|
||||
color?: string;
|
||||
billingPeriod?: string;
|
||||
billingPeriodInterval?: number;
|
||||
currency: string;
|
||||
}
|
||||
|
||||
export interface ProductTracksData {
|
||||
|
|
|
@ -144,6 +144,10 @@ async function fetchSearchResults(
|
|||
featuredImage: product.featured_image,
|
||||
productCategory: product.product_category,
|
||||
color: product.color,
|
||||
billingPeriod: product.billing_period,
|
||||
billingPeriodInterval:
|
||||
product.billing_period_interval,
|
||||
currency: product.currency,
|
||||
};
|
||||
}
|
||||
);
|
||||
|
@ -407,6 +411,7 @@ const subscriptionToProduct = ( subscription: Subscription ): Product => {
|
|||
averageRating: null,
|
||||
reviewsCount: null,
|
||||
isInstallable: false,
|
||||
currency: '',
|
||||
};
|
||||
};
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
Significance: patch
|
||||
Type: update
|
||||
|
||||
Product cards in the in-app marketplace show currency and billing period data dynamically, based on data received from WooCommerce.com
|
Loading…
Reference in New Issue