@stigg/react-sdk 5.28.4 → 5.30.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/paywall/Paywall.d.ts +3 -2
- package/dist/components/paywall/PaywallContainer.d.ts +3 -2
- package/dist/components/paywall/PlanOffering.d.ts +3 -2
- package/dist/components/paywall/PlanOfferingButton.d.ts +3 -2
- package/dist/components/paywall/hooks/useLoadPaywallData.d.ts +3 -2
- package/dist/components/paywall/types.d.ts +8 -0
- package/dist/components/paywall/utils/mapPaywallData.d.ts +3 -2
- package/dist/components/utils/priceTierUtils.d.ts +14 -3
- package/dist/react-sdk.cjs.development.js +106 -34
- package/dist/react-sdk.cjs.development.js.map +1 -1
- package/dist/react-sdk.cjs.production.min.js +1 -1
- package/dist/react-sdk.cjs.production.min.js.map +1 -1
- package/dist/react-sdk.esm.js +106 -34
- package/dist/react-sdk.esm.js.map +1 -1
- package/package.json +2 -2
- package/src/components/paywall/Paywall.tsx +11 -2
- package/src/components/paywall/PaywallContainer.tsx +11 -1
- package/src/components/paywall/PlanOffering.tsx +11 -2
- package/src/components/paywall/PlanOfferingButton.tsx +9 -2
- package/src/components/paywall/hooks/useLoadPaywallData.ts +4 -2
- package/src/components/paywall/types.ts +12 -0
- package/src/components/paywall/utils/mapPaywallData.ts +13 -3
- package/src/components/utils/priceTierUtils.ts +54 -13
package/package.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "5.
|
|
2
|
+
"version": "5.30.0",
|
|
3
3
|
"license": "MIT",
|
|
4
4
|
"main": "dist/index.js",
|
|
5
5
|
"typings": "dist/index.d.ts",
|
|
@@ -114,7 +114,7 @@
|
|
|
114
114
|
"@emotion/react": "^11.10.5",
|
|
115
115
|
"@emotion/styled": "^11.10.5",
|
|
116
116
|
"@mui/material": "^5.12.0",
|
|
117
|
-
"@stigg/js-client-sdk": "3.
|
|
117
|
+
"@stigg/js-client-sdk": "3.36.0",
|
|
118
118
|
"@stripe/react-stripe-js": "^2.1.1",
|
|
119
119
|
"@stripe/stripe-js": "^1.54.1",
|
|
120
120
|
"@types/styled-components": "^5.1.26",
|
|
@@ -10,6 +10,7 @@ import {
|
|
|
10
10
|
PaywallPlan,
|
|
11
11
|
SubscribeIntentionType,
|
|
12
12
|
SelectDefaultTierIndexFn,
|
|
13
|
+
CurrentSubscriptionOverride,
|
|
13
14
|
} from './types';
|
|
14
15
|
import { PaywallLocalization } from './paywallTextOverrides';
|
|
15
16
|
import { PoweredByStigg } from '../common/PoweredByStigg';
|
|
@@ -49,6 +50,7 @@ type PaywallProps = {
|
|
|
49
50
|
plans: PaywallPlan[];
|
|
50
51
|
customer: Customer | null;
|
|
51
52
|
currentSubscription: Subscription | null;
|
|
53
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverride | null;
|
|
52
54
|
selectedBillingPeriod: BillingPeriod;
|
|
53
55
|
highlightedPlanId?: string;
|
|
54
56
|
onBillingPeriodChanged: (billingPeriod: BillingPeriod) => void;
|
|
@@ -75,6 +77,7 @@ export const Paywall = ({
|
|
|
75
77
|
locale,
|
|
76
78
|
shouldHidePlan,
|
|
77
79
|
selectDefaultTierIndex,
|
|
80
|
+
currentSubscriptionOverride,
|
|
78
81
|
}: PaywallProps) => {
|
|
79
82
|
const { stigg } = useStiggContext();
|
|
80
83
|
const discountRate = calculatePaywallDiscountRate(plans);
|
|
@@ -123,11 +126,16 @@ export const Paywall = ({
|
|
|
123
126
|
return (
|
|
124
127
|
!isCustomerInCustomPlan &&
|
|
125
128
|
plansToShow.some((plan) => {
|
|
126
|
-
const tiers = getTiersPerUnitQuantities(
|
|
129
|
+
const tiers = getTiersPerUnitQuantities({
|
|
130
|
+
plan,
|
|
131
|
+
billingPeriod: selectedBillingPeriod,
|
|
132
|
+
currentSubscription,
|
|
133
|
+
currentSubscriptionOverride,
|
|
134
|
+
});
|
|
127
135
|
return Object.values(tiers).length > 0;
|
|
128
136
|
})
|
|
129
137
|
);
|
|
130
|
-
}, [selectedBillingPeriod, currentSubscription, isCustomerInCustomPlan, plansToShow]);
|
|
138
|
+
}, [selectedBillingPeriod, currentSubscription, currentSubscriptionOverride, isCustomerInCustomPlan, plansToShow]);
|
|
131
139
|
|
|
132
140
|
const withTrialLeftRow = plansToShow.some((plan) => {
|
|
133
141
|
return plan.isCurrentCustomerPlan && plan.trialDaysLeft;
|
|
@@ -156,6 +164,7 @@ export const Paywall = ({
|
|
|
156
164
|
plan={plan}
|
|
157
165
|
withStartingAtRow={withStartingAtRow}
|
|
158
166
|
currentSubscription={currentSubscription}
|
|
167
|
+
currentSubscriptionOverride={currentSubscriptionOverride}
|
|
159
168
|
billingPeriod={selectedBillingPeriod}
|
|
160
169
|
isHighlighted={plan.id === highlightedPlanId}
|
|
161
170
|
isCustomerOnTrial={isCustomerOnTrial}
|
|
@@ -2,7 +2,12 @@ import React from 'react';
|
|
|
2
2
|
import { BillingPeriod } from '@stigg/js-client-sdk';
|
|
3
3
|
import { Paywall } from './Paywall';
|
|
4
4
|
import { useLoadPaywallData } from './hooks/useLoadPaywallData';
|
|
5
|
-
import {
|
|
5
|
+
import {
|
|
6
|
+
ShouldHidePlanFn,
|
|
7
|
+
OnPlanSelectedCallbackFn,
|
|
8
|
+
SelectDefaultTierIndexFn,
|
|
9
|
+
CurrentSubscriptionOverrideFn,
|
|
10
|
+
} from './types';
|
|
6
11
|
import { getResolvedPaywallLocalize, PaywallLocalization } from './paywallTextOverrides';
|
|
7
12
|
import { DeepPartial } from '../../types';
|
|
8
13
|
import { PaywallLoader } from './PaywallLoader';
|
|
@@ -25,6 +30,7 @@ export type PaywallContainerProps = {
|
|
|
25
30
|
billingCountryCode?: string;
|
|
26
31
|
shouldHidePlan?: ShouldHidePlanFn;
|
|
27
32
|
selectDefaultTierIndex?: SelectDefaultTierIndexFn;
|
|
33
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverrideFn;
|
|
28
34
|
};
|
|
29
35
|
|
|
30
36
|
export const PaywallContainer = ({
|
|
@@ -39,6 +45,7 @@ export const PaywallContainer = ({
|
|
|
39
45
|
billingCountryCode,
|
|
40
46
|
shouldHidePlan,
|
|
41
47
|
selectDefaultTierIndex,
|
|
48
|
+
currentSubscriptionOverride: currentSubscriptionOverrideFn,
|
|
42
49
|
}: PaywallContainerProps) => {
|
|
43
50
|
const hasCustomerPortalContext = useCheckContextExists(CustomerPortalContext);
|
|
44
51
|
let isCustomerPortalLoading = false;
|
|
@@ -52,6 +59,7 @@ export const PaywallContainer = ({
|
|
|
52
59
|
plans,
|
|
53
60
|
customer,
|
|
54
61
|
currentSubscription,
|
|
62
|
+
currentSubscriptionOverride,
|
|
55
63
|
isCustomerOnTrial,
|
|
56
64
|
isLoading,
|
|
57
65
|
selectedBillingPeriod,
|
|
@@ -65,6 +73,7 @@ export const PaywallContainer = ({
|
|
|
65
73
|
showOnlyEligiblePlans,
|
|
66
74
|
billingCountryCode,
|
|
67
75
|
preferredBillingPeriod,
|
|
76
|
+
currentSubscriptionOverrideFn,
|
|
68
77
|
});
|
|
69
78
|
const paywallLocale = getResolvedPaywallLocalize(textOverrides);
|
|
70
79
|
const handlePeriodChange = (billingPeriod: BillingPeriod) => {
|
|
@@ -82,6 +91,7 @@ export const PaywallContainer = ({
|
|
|
82
91
|
plans={plans}
|
|
83
92
|
customer={customer}
|
|
84
93
|
currentSubscription={currentSubscription}
|
|
94
|
+
currentSubscriptionOverride={currentSubscriptionOverride}
|
|
85
95
|
selectedBillingPeriod={selectedBillingPeriod}
|
|
86
96
|
onBillingPeriodChanged={handlePeriodChange}
|
|
87
97
|
availableBillingPeriods={availableBillingPeriods}
|
|
@@ -5,7 +5,7 @@ import classNames from 'classnames';
|
|
|
5
5
|
import Grid from '@mui/material/Grid';
|
|
6
6
|
import { PlanEntitlements } from './PlanEntitlements';
|
|
7
7
|
import { PlanOfferingButton } from './PlanOfferingButton';
|
|
8
|
-
import { PaywallPlan, SelectDefaultTierIndexFn, SubscribeIntentionType } from './types';
|
|
8
|
+
import { CurrentSubscriptionOverride, PaywallPlan, SelectDefaultTierIndexFn, SubscribeIntentionType } from './types';
|
|
9
9
|
import { PaywallLocalization } from './paywallTextOverrides';
|
|
10
10
|
import { flexLayoutMapper } from '../../theme/getResolvedTheme';
|
|
11
11
|
import { Typography } from '../common/Typography';
|
|
@@ -75,6 +75,7 @@ type PlanOfferingProps = {
|
|
|
75
75
|
plan: PaywallPlan;
|
|
76
76
|
billingPeriod: BillingPeriod;
|
|
77
77
|
currentSubscription: Subscription | null;
|
|
78
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverride | null;
|
|
78
79
|
isHighlighted: boolean;
|
|
79
80
|
shouldShowDescriptionSection: boolean;
|
|
80
81
|
hasAnnuallyPrice: boolean;
|
|
@@ -128,6 +129,7 @@ export function PlanOffering({
|
|
|
128
129
|
billingPeriod,
|
|
129
130
|
isHighlighted,
|
|
130
131
|
currentSubscription,
|
|
132
|
+
currentSubscriptionOverride,
|
|
131
133
|
shouldShowDescriptionSection,
|
|
132
134
|
hasMonthlyPrice,
|
|
133
135
|
hasAnnuallyPrice,
|
|
@@ -161,7 +163,13 @@ export function PlanOffering({
|
|
|
161
163
|
}
|
|
162
164
|
|
|
163
165
|
const [perUnitQuantityByFeature, setPerUnitQuantityByFeature] = useState<Record<string, number>>(
|
|
164
|
-
getTiersPerUnitQuantities(
|
|
166
|
+
getTiersPerUnitQuantities({
|
|
167
|
+
plan,
|
|
168
|
+
billingPeriod,
|
|
169
|
+
currentSubscription,
|
|
170
|
+
currentSubscriptionOverride,
|
|
171
|
+
selectDefaultTierIndex,
|
|
172
|
+
}),
|
|
165
173
|
);
|
|
166
174
|
|
|
167
175
|
const onPlanButtonClick = (intentionType: SubscribeIntentionType) => {
|
|
@@ -214,6 +222,7 @@ export function PlanOffering({
|
|
|
214
222
|
customer={customer}
|
|
215
223
|
plan={plan}
|
|
216
224
|
currentSubscription={currentSubscription}
|
|
225
|
+
currentSubscriptionOverride={currentSubscriptionOverride}
|
|
217
226
|
billingPeriod={billingPeriod}
|
|
218
227
|
isCustomerOnTrial={isCustomerOnTrial}
|
|
219
228
|
onPlanSelected={onPlanButtonClick}
|
|
@@ -4,7 +4,7 @@ import { isFunction } from 'lodash';
|
|
|
4
4
|
import ClipLoader from 'react-spinners/ClipLoader';
|
|
5
5
|
import styled from '@emotion/styled/macro';
|
|
6
6
|
import { css, useTheme } from '@emotion/react';
|
|
7
|
-
import { PaywallPlan, SubscribeIntentionType } from './types';
|
|
7
|
+
import { CurrentSubscriptionOverride, PaywallPlan, SubscribeIntentionType } from './types';
|
|
8
8
|
import { PaywallLocalization } from './paywallTextOverrides';
|
|
9
9
|
import { flexLayoutMapper } from '../../theme/getResolvedTheme';
|
|
10
10
|
import { Typography } from '../common/Typography';
|
|
@@ -77,6 +77,7 @@ type PlanOfferingButtonProps = {
|
|
|
77
77
|
customer: Customer | null;
|
|
78
78
|
plan: PaywallPlan;
|
|
79
79
|
currentSubscription: Subscription | null;
|
|
80
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverride | null;
|
|
80
81
|
billingPeriod: BillingPeriod;
|
|
81
82
|
isCustomerOnTrial: boolean;
|
|
82
83
|
paywallLocale: PaywallLocalization;
|
|
@@ -95,6 +96,7 @@ export function PlanOfferingButton({
|
|
|
95
96
|
paywallLocale,
|
|
96
97
|
withTrialLeftRow,
|
|
97
98
|
currentSubscription,
|
|
99
|
+
currentSubscriptionOverride,
|
|
98
100
|
perUnitQuantityByFeature,
|
|
99
101
|
}: PlanOfferingButtonProps) {
|
|
100
102
|
const theme = useTheme();
|
|
@@ -142,7 +144,12 @@ export function PlanOfferingButton({
|
|
|
142
144
|
isSameBillingPeriod ||
|
|
143
145
|
(plan.pricingType && [PricingType.Free, PricingType.Custom].includes(plan.pricingType))
|
|
144
146
|
) {
|
|
145
|
-
const planComparison = compareSelectedTierToCurrentTier(
|
|
147
|
+
const planComparison = compareSelectedTierToCurrentTier({
|
|
148
|
+
perUnitQuantityByFeature,
|
|
149
|
+
plan,
|
|
150
|
+
currentSubscription,
|
|
151
|
+
currentSubscriptionOverride,
|
|
152
|
+
});
|
|
146
153
|
switch (planComparison) {
|
|
147
154
|
case PriceTierComparison.Lower:
|
|
148
155
|
buttonProps.intentionType = SubscribeIntentionType.CHANGE_UNIT_QUANTITY;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { BillingPeriod, Paywall } from '@stigg/js-client-sdk';
|
|
2
2
|
import { useEffect, useState } from 'react';
|
|
3
3
|
import logger from '../../../services/logger';
|
|
4
|
-
import { PaywallData } from '../types';
|
|
4
|
+
import { CurrentSubscriptionOverrideFn, PaywallData } from '../types';
|
|
5
5
|
import { computeBillingPeriods } from '../utils/computeDefaultBillingPeriod';
|
|
6
6
|
import { mapPaywallData } from '../utils/mapPaywallData';
|
|
7
7
|
import { useStiggContext } from '../../../hooks/useStiggContext';
|
|
@@ -12,6 +12,7 @@ type UseLoadPaywallDataProps = {
|
|
|
12
12
|
showOnlyEligiblePlans?: boolean;
|
|
13
13
|
billingCountryCode?: string;
|
|
14
14
|
preferredBillingPeriod?: BillingPeriod;
|
|
15
|
+
currentSubscriptionOverrideFn?: CurrentSubscriptionOverrideFn;
|
|
15
16
|
};
|
|
16
17
|
|
|
17
18
|
export function useLoadPaywallData({
|
|
@@ -20,6 +21,7 @@ export function useLoadPaywallData({
|
|
|
20
21
|
showOnlyEligiblePlans,
|
|
21
22
|
billingCountryCode,
|
|
22
23
|
preferredBillingPeriod,
|
|
24
|
+
currentSubscriptionOverrideFn,
|
|
23
25
|
}: UseLoadPaywallDataProps): PaywallData {
|
|
24
26
|
const { stigg, locale } = useStiggContext();
|
|
25
27
|
const [selectedBillingPeriod, setSelectedBillingPeriod] = useState(BillingPeriod.Annually);
|
|
@@ -57,7 +59,7 @@ export function useLoadPaywallData({
|
|
|
57
59
|
void loadPaywall();
|
|
58
60
|
}, [stigg, productId, stigg.isCustomerLoaded, billingCountryCode, resourceId, preferredBillingPeriod]);
|
|
59
61
|
|
|
60
|
-
const paywallData = mapPaywallData(paywall, showOnlyEligiblePlans);
|
|
62
|
+
const paywallData = mapPaywallData(paywall, showOnlyEligiblePlans, currentSubscriptionOverrideFn);
|
|
61
63
|
|
|
62
64
|
return {
|
|
63
65
|
customer: paywall?.customer || null,
|
|
@@ -14,6 +14,7 @@ export type PaywallData = {
|
|
|
14
14
|
plans: PaywallPlan[] | null;
|
|
15
15
|
customer: Customer | null;
|
|
16
16
|
currentSubscription: Subscription | null;
|
|
17
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverride | null;
|
|
17
18
|
isCustomerOnTrial: boolean;
|
|
18
19
|
isLoading: boolean;
|
|
19
20
|
selectedBillingPeriod: BillingPeriod;
|
|
@@ -23,6 +24,11 @@ export type PaywallData = {
|
|
|
23
24
|
configuration?: CustomizedTheme;
|
|
24
25
|
};
|
|
25
26
|
|
|
27
|
+
export type CurrentSubscriptionOverride = {
|
|
28
|
+
planId: string;
|
|
29
|
+
billableFeatures: BillableFeature[];
|
|
30
|
+
};
|
|
31
|
+
|
|
26
32
|
export enum SubscribeIntentionType {
|
|
27
33
|
START_TRIAL = 'START_TRIAL',
|
|
28
34
|
UPGRADE_TRIAL_TO_PAID = 'UPGRADE_TRIAL_TO_PAID',
|
|
@@ -64,4 +70,10 @@ export type OnPlanSelectedCallbackFn = ({
|
|
|
64
70
|
|
|
65
71
|
export type ShouldHidePlanFn = ({ plan }: { plan: PaywallPlan }) => boolean | Promise<boolean>;
|
|
66
72
|
|
|
73
|
+
export type CurrentSubscriptionOverrideFn = ({
|
|
74
|
+
currentSubscription,
|
|
75
|
+
}: {
|
|
76
|
+
currentSubscription: Subscription | null;
|
|
77
|
+
}) => CurrentSubscriptionOverride | null | undefined;
|
|
78
|
+
|
|
67
79
|
export type SelectDefaultTierIndexFn = ({ plan }: { plan: PaywallPlan }) => number;
|
|
@@ -8,7 +8,7 @@ import {
|
|
|
8
8
|
} from '@stigg/js-client-sdk';
|
|
9
9
|
import isNil from 'lodash/isNil';
|
|
10
10
|
import sortBy from 'lodash/sortBy';
|
|
11
|
-
import { PaywallPlan } from '../types';
|
|
11
|
+
import { CurrentSubscriptionOverride, CurrentSubscriptionOverrideFn, PaywallPlan } from '../types';
|
|
12
12
|
import { calculateTrialDaysLeft } from './calculateTrialDaysLeft';
|
|
13
13
|
import { BillingPeriodChangeVariables, DeepPartial, DowngradeChangeVariables } from '../../../types';
|
|
14
14
|
import { StiggTheme } from '../../../theme/types';
|
|
@@ -39,16 +39,23 @@ function getCustomerSubscriptionDetails(activeSubscriptions?: Subscription[] | n
|
|
|
39
39
|
type PaywallData = {
|
|
40
40
|
currentPlan?: Plan;
|
|
41
41
|
currentSubscription: Subscription | null;
|
|
42
|
+
currentSubscriptionOverride: CurrentSubscriptionOverride | null | undefined;
|
|
42
43
|
isCustomerOnTrial: boolean;
|
|
43
44
|
plans: PaywallPlan[];
|
|
44
45
|
paywallConfiguration?: DeepPartial<StiggTheme>;
|
|
45
46
|
};
|
|
46
47
|
|
|
47
|
-
export function mapPaywallData(
|
|
48
|
+
export function mapPaywallData(
|
|
49
|
+
paywall: Paywall | null,
|
|
50
|
+
showOnlyEligiblePlans?: boolean,
|
|
51
|
+
currentSubscriptionOverrideFn?: CurrentSubscriptionOverrideFn,
|
|
52
|
+
): PaywallData {
|
|
48
53
|
const { plans, currency, configuration, customer, activeSubscriptions, paywallCalculatedPricePoints } = paywall || {};
|
|
49
54
|
const { currentSubscription, currentPlan, isCustomerOnTrial, trialDaysLeft } =
|
|
50
55
|
getCustomerSubscriptionDetails(activeSubscriptions);
|
|
51
56
|
|
|
57
|
+
const currentSubscriptionOverride = currentSubscriptionOverrideFn?.({ currentSubscription });
|
|
58
|
+
|
|
52
59
|
const scheduledUpdates = currentSubscription?.scheduledUpdates || [];
|
|
53
60
|
const currentCustomerPlanBillingPeriod = currentSubscription?.price?.billingPeriod;
|
|
54
61
|
const downgradeSchedule = scheduledUpdates.find(
|
|
@@ -62,7 +69,9 @@ export function mapPaywallData(paywall: Paywall | null, showOnlyEligiblePlans?:
|
|
|
62
69
|
const eligibleForProductTrial = customer?.eligibleForTrial?.find(
|
|
63
70
|
(productTrial) => productTrial.productId === plan.product.id,
|
|
64
71
|
);
|
|
65
|
-
const isCurrentCustomerPlan =
|
|
72
|
+
const isCurrentCustomerPlan = currentSubscriptionOverride?.planId
|
|
73
|
+
? currentSubscriptionOverride?.planId === plan.id
|
|
74
|
+
: plan.id === currentPlan?.id;
|
|
66
75
|
|
|
67
76
|
const isNextPlan = (currentBillingPeriod: BillingPeriod) => {
|
|
68
77
|
const downgradeVariables = downgradeSchedule?.scheduleVariables as DowngradeChangeVariables;
|
|
@@ -109,6 +118,7 @@ export function mapPaywallData(paywall: Paywall | null, showOnlyEligiblePlans?:
|
|
|
109
118
|
return {
|
|
110
119
|
currentPlan,
|
|
111
120
|
currentSubscription,
|
|
121
|
+
currentSubscriptionOverride,
|
|
112
122
|
isCustomerOnTrial,
|
|
113
123
|
plans: paywallPlans,
|
|
114
124
|
paywallConfiguration,
|
|
@@ -2,7 +2,7 @@ import { BillingModel, TiersMode, BillingPeriod, Price, PriceTierFragment, Subsc
|
|
|
2
2
|
import isNil from 'lodash/isNil';
|
|
3
3
|
import { sum } from 'lodash';
|
|
4
4
|
import { PaywallPlan } from '../paywall';
|
|
5
|
-
import { SelectDefaultTierIndexFn } from '../paywall/types';
|
|
5
|
+
import { CurrentSubscriptionOverride, SelectDefaultTierIndexFn } from '../paywall/types';
|
|
6
6
|
|
|
7
7
|
export function getPriceFeatureUnit(price: Price) {
|
|
8
8
|
if (!price.feature) {
|
|
@@ -131,12 +131,19 @@ export function isQuantityInFirstTier(tiers: PriceTierFragment[] | null | undefi
|
|
|
131
131
|
return tiers?.[0].upTo && quantity <= tiers[0].upTo;
|
|
132
132
|
}
|
|
133
133
|
|
|
134
|
-
export function getTiersPerUnitQuantities(
|
|
135
|
-
plan
|
|
136
|
-
billingPeriod
|
|
137
|
-
currentSubscription
|
|
138
|
-
|
|
139
|
-
|
|
134
|
+
export function getTiersPerUnitQuantities({
|
|
135
|
+
plan,
|
|
136
|
+
billingPeriod,
|
|
137
|
+
currentSubscription,
|
|
138
|
+
currentSubscriptionOverride,
|
|
139
|
+
selectDefaultTierIndex,
|
|
140
|
+
}: {
|
|
141
|
+
plan: PaywallPlan;
|
|
142
|
+
billingPeriod: BillingPeriod;
|
|
143
|
+
currentSubscription: Subscription | null;
|
|
144
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverride | null;
|
|
145
|
+
selectDefaultTierIndex?: SelectDefaultTierIndexFn;
|
|
146
|
+
}): Record<string, number> {
|
|
140
147
|
const planTierPrices = plan.pricePoints.filter(
|
|
141
148
|
(price) => price.billingPeriod === billingPeriod && price.isTieredPrice,
|
|
142
149
|
);
|
|
@@ -161,6 +168,15 @@ export function getTiersPerUnitQuantities(
|
|
|
161
168
|
}
|
|
162
169
|
}
|
|
163
170
|
|
|
171
|
+
if (currentSubscriptionOverride?.planId === plan.id) {
|
|
172
|
+
const billableFeature = currentSubscriptionOverride.billableFeatures.find(
|
|
173
|
+
(billableFeature) => billableFeature.featureId === featureId,
|
|
174
|
+
);
|
|
175
|
+
if (billableFeature) {
|
|
176
|
+
quantity = billableFeature.quantity;
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
|
|
164
180
|
const result: Record<string, number> = {};
|
|
165
181
|
result[featureId] = quantity;
|
|
166
182
|
|
|
@@ -176,22 +192,47 @@ export enum PriceTierComparison {
|
|
|
176
192
|
Higher = 1,
|
|
177
193
|
}
|
|
178
194
|
|
|
179
|
-
export function compareSelectedTierToCurrentTier(
|
|
180
|
-
perUnitQuantityByFeature
|
|
181
|
-
|
|
182
|
-
|
|
195
|
+
export function compareSelectedTierToCurrentTier({
|
|
196
|
+
perUnitQuantityByFeature,
|
|
197
|
+
plan,
|
|
198
|
+
currentSubscription,
|
|
199
|
+
currentSubscriptionOverride,
|
|
200
|
+
}: {
|
|
201
|
+
perUnitQuantityByFeature: Record<string, number>;
|
|
202
|
+
plan: PaywallPlan;
|
|
203
|
+
currentSubscription: Subscription | null;
|
|
204
|
+
currentSubscriptionOverride?: CurrentSubscriptionOverride | null;
|
|
205
|
+
}): PriceTierComparison {
|
|
183
206
|
if (!currentSubscription) {
|
|
184
207
|
return PriceTierComparison.Equal;
|
|
185
208
|
}
|
|
186
209
|
|
|
187
|
-
|
|
210
|
+
let currentTierPrice = currentSubscription.prices.find(
|
|
188
211
|
(price) => price.pricingModel === BillingModel.PerUnit && price.tiersMode,
|
|
189
212
|
);
|
|
213
|
+
|
|
214
|
+
const isCurrentPlanOverride = plan.id === currentSubscriptionOverride?.planId;
|
|
215
|
+
if (isCurrentPlanOverride) {
|
|
216
|
+
currentTierPrice =
|
|
217
|
+
plan.pricePoints.find((price) => price.pricingModel === BillingModel.PerUnit && price.tiersMode) ??
|
|
218
|
+
currentTierPrice;
|
|
219
|
+
}
|
|
220
|
+
|
|
190
221
|
if (!currentTierPrice) {
|
|
191
222
|
return PriceTierComparison.Equal;
|
|
192
223
|
}
|
|
193
224
|
|
|
194
|
-
const { featureId, unitQuantity
|
|
225
|
+
const { featureId, unitQuantity } = currentTierPrice.feature!;
|
|
226
|
+
let oldQuantity = unitQuantity;
|
|
227
|
+
|
|
228
|
+
if (isCurrentPlanOverride) {
|
|
229
|
+
const billableFeature = currentSubscriptionOverride?.billableFeatures?.find(
|
|
230
|
+
(billableFeature) => billableFeature.featureId === featureId,
|
|
231
|
+
);
|
|
232
|
+
if (billableFeature) {
|
|
233
|
+
oldQuantity = billableFeature.quantity;
|
|
234
|
+
}
|
|
235
|
+
}
|
|
195
236
|
|
|
196
237
|
if (isNil(oldQuantity)) {
|
|
197
238
|
return PriceTierComparison.Equal;
|