@stigg/react-sdk 4.4.0-beta.9 → 4.4.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.
Files changed (91) hide show
  1. package/dist/components/checkout/Checkout.d.ts +3 -2
  2. package/dist/components/checkout/CheckoutContainer.d.ts +4 -2
  3. package/dist/components/checkout/CheckoutProvider.d.ts +3 -2
  4. package/dist/components/checkout/components/DowngradeToFreeContainer.d.ts +3 -7
  5. package/dist/components/checkout/components/StyledArrow.d.ts +5 -0
  6. package/dist/components/checkout/hooks/useCheckoutModel.d.ts +2 -0
  7. package/dist/components/checkout/hooks/useLoadCheckout.d.ts +3 -1
  8. package/dist/components/checkout/hooks/usePreviewSubscription.d.ts +17 -8
  9. package/dist/components/checkout/progressBar/CheckoutProgressBar.style.d.ts +1 -0
  10. package/dist/components/checkout/promotionCode/AddPromotionCode.d.ts +2 -4
  11. package/dist/components/checkout/promotionCode/AddPromotionCodeButton.d.ts +2 -1
  12. package/dist/components/checkout/promotionCode/PromotionCodeSection.d.ts +6 -2
  13. package/dist/components/checkout/steps/plan/BillingPeriodPicker.d.ts +1 -1
  14. package/dist/components/checkout/steps/plan/CheckoutPlanStep.d.ts +2 -1
  15. package/dist/components/checkout/summary/CheckoutSummary.d.ts +1 -1
  16. package/dist/components/checkout/summary/components/CheckoutCaptions.d.ts +2 -2
  17. package/dist/components/checkout/summary/components/LineItems.d.ts +12 -8
  18. package/dist/components/checkout/textOverrides.d.ts +63 -20
  19. package/dist/components/checkout/theme.d.ts +0 -1
  20. package/dist/components/checkout/types.d.ts +7 -1
  21. package/dist/components/common/TiersSelectContainer.d.ts +1 -2
  22. package/dist/components/common/Typography.d.ts +2 -2
  23. package/dist/components/common/customIcons.d.ts +2 -0
  24. package/dist/components/customerPortal/subscriptionOverview/subscriptionView/SubscriptionView.style.d.ts +1 -1
  25. package/dist/components/paywall/PlanPrice.d.ts +1 -1
  26. package/dist/components/utils/currencyUtils.d.ts +2 -1
  27. package/dist/components/utils/getFeatureName.d.ts +1 -0
  28. package/dist/react-sdk.cjs.development.js +1027 -559
  29. package/dist/react-sdk.cjs.development.js.map +1 -1
  30. package/dist/react-sdk.cjs.production.min.js +1 -1
  31. package/dist/react-sdk.cjs.production.min.js.map +1 -1
  32. package/dist/react-sdk.esm.js +1041 -582
  33. package/dist/react-sdk.esm.js.map +1 -1
  34. package/dist/stories/mocks/checkout/consts.d.ts +11 -0
  35. package/dist/stories/mocks/checkout/mockCheckoutPreview.d.ts +2 -0
  36. package/dist/stories/mocks/checkout/mockCheckoutState.d.ts +2 -0
  37. package/dist/theme/getResolvedTheme.d.ts +1 -0
  38. package/dist/theme/types.d.ts +1 -0
  39. package/package.json +28 -20
  40. package/src/assets/coupon.svg +6 -0
  41. package/src/assets/pay-as-you-go-charge.svg +11 -0
  42. package/src/components/checkout/Checkout.tsx +5 -2
  43. package/src/components/checkout/CheckoutContainer.tsx +18 -12
  44. package/src/components/checkout/CheckoutProvider.tsx +5 -3
  45. package/src/components/checkout/components/DowngradeToFreeContainer.tsx +33 -36
  46. package/src/components/checkout/components/StyledArrow.tsx +9 -0
  47. package/src/components/checkout/hooks/useCheckoutModel.ts +12 -2
  48. package/src/components/checkout/hooks/useLoadCheckout.ts +10 -2
  49. package/src/components/checkout/hooks/usePreviewSubscription.ts +102 -50
  50. package/src/components/checkout/planHeader/PlanHeader.tsx +18 -25
  51. package/src/components/checkout/progressBar/CheckoutProgressBar.style.ts +11 -12
  52. package/src/components/checkout/progressBar/CheckoutProgressBar.tsx +7 -6
  53. package/src/components/checkout/promotionCode/AddPromotionCode.tsx +32 -9
  54. package/src/components/checkout/promotionCode/AddPromotionCodeButton.tsx +15 -11
  55. package/src/components/checkout/promotionCode/AppliedPromotionCode.tsx +4 -3
  56. package/src/components/checkout/promotionCode/PromotionCodeSection.tsx +21 -7
  57. package/src/components/checkout/steps/addons/CheckoutAddonsStep.style.tsx +0 -1
  58. package/src/components/checkout/steps/addons/CheckoutAddonsStep.tsx +4 -3
  59. package/src/components/checkout/steps/payment/PaymentMethods.style.ts +4 -1
  60. package/src/components/checkout/steps/payment/PaymentStep.tsx +0 -1
  61. package/src/components/checkout/steps/plan/BillingPeriodPicker.style.tsx +3 -2
  62. package/src/components/checkout/steps/plan/BillingPeriodPicker.tsx +5 -2
  63. package/src/components/checkout/steps/plan/CheckoutChargeList.tsx +35 -14
  64. package/src/components/checkout/steps/plan/CheckoutPlanStep.tsx +10 -5
  65. package/src/components/checkout/summary/CheckoutSuccess.tsx +1 -1
  66. package/src/components/checkout/summary/CheckoutSummary.tsx +143 -46
  67. package/src/components/checkout/summary/components/CheckoutCaptions.tsx +38 -15
  68. package/src/components/checkout/summary/components/LineItems.tsx +77 -28
  69. package/src/components/checkout/textOverrides.ts +107 -27
  70. package/src/components/checkout/theme.ts +0 -4
  71. package/src/components/checkout/types.ts +15 -1
  72. package/src/components/common/Icon.tsx +4 -6
  73. package/src/components/common/TiersSelectContainer.tsx +7 -8
  74. package/src/components/common/Typography.tsx +12 -3
  75. package/src/components/common/customIcons.ts +2 -0
  76. package/src/components/common/mapExternalTheme.ts +1 -2
  77. package/src/components/customerPortal/paywall/CustomerPortalPaywall.style.ts +4 -3
  78. package/src/components/paywall/PlanOfferingButton.tsx +6 -8
  79. package/src/components/paywall/PlanPrice.tsx +14 -17
  80. package/src/components/utils/currencyUtils.ts +4 -2
  81. package/src/components/utils/getFeatureName.ts +13 -5
  82. package/src/stories/Checkout.stories.tsx +37 -6
  83. package/src/stories/CustomerPortal.stories.tsx +2 -2
  84. package/src/stories/mocks/checkout/consts.ts +15 -0
  85. package/src/stories/mocks/checkout/mockCheckoutPreview.ts +138 -0
  86. package/src/stories/mocks/checkout/mockCheckoutState.ts +206 -0
  87. package/src/theme/Theme.tsx +10 -1
  88. package/src/theme/getResolvedTheme.ts +1 -0
  89. package/src/theme/types.ts +1 -0
  90. package/dist/components/checkout/planHeader/PlanHeader.style.d.ts +0 -25
  91. package/src/components/checkout/planHeader/PlanHeader.style.tsx +0 -23
@@ -1,10 +1,10 @@
1
+ import React, { useEffect, useState } from 'react';
2
+ import styled from '@emotion/styled/macro';
3
+ import { BillingPeriod, PriceTierFragment } from '@stigg/js-client-sdk';
1
4
  import { PaywallPlan } from './types';
2
5
  import { PaywallLocalization } from './paywallTextOverrides';
3
6
  import { getPlanPrice } from '../utils/getPlanPrice';
4
7
  import { Typography } from '../common/Typography';
5
- import React, { useEffect, useState } from 'react';
6
- import styled from '@emotion/styled/macro';
7
- import { BillingPeriod, PriceTierFragment } from '@stigg/js-client-sdk';
8
8
  import { TiersSelectContainer } from '../common/TiersSelectContainer';
9
9
 
10
10
  const EMPTY_CHAR = '‎';
@@ -38,7 +38,7 @@ function PriceBillingPeriod({
38
38
  hasAnnuallyPrice,
39
39
  paywallLocale,
40
40
  }: PriceBillingPeriodProps) {
41
- const hasPrice = plan.pricePoints.find(pricePoint => pricePoint.billingPeriod === billingPeriod);
41
+ const hasPrice = plan.pricePoints.find((pricePoint) => pricePoint.billingPeriod === billingPeriod);
42
42
 
43
43
  let content = EMPTY_CHAR;
44
44
  if (hasPrice && hasMonthlyPrice && hasAnnuallyPrice) {
@@ -79,7 +79,7 @@ export const PlanPrice = ({
79
79
  hasAnnuallyPrice: boolean;
80
80
  locale: string;
81
81
  }) => {
82
- const { price, unit, tiers, tierUnits } = getPlanPrice(
82
+ const { price, unit, tiers } = getPlanPrice(
83
83
  plan,
84
84
  billingPeriod,
85
85
  paywallLocale,
@@ -87,18 +87,17 @@ export const PlanPrice = ({
87
87
  hasMonthlyPrice,
88
88
  selectedTierByFeature,
89
89
  );
90
-
91
90
  const [selectedTier, setSelectedTier] = useState<PriceTierFragment>();
92
91
 
93
- useEffect(() => {
94
- setSelectedTier(selectedTierByFeature[featureId!]);
95
- }, [selectedTierByFeature]);
96
-
97
92
  // We currently only support prices with one tier - so we select the first one
98
- const tieredPrice = plan.pricePoints.find(planPrice => {
93
+ const tieredPrice = plan.pricePoints.find((planPrice) => {
99
94
  return planPrice.billingPeriod === billingPeriod && planPrice.isTieredPrice;
100
95
  });
101
- const featureId = tieredPrice ? tieredPrice!.feature!.featureId : undefined;
96
+ const featureId = tieredPrice ? tieredPrice.feature!.featureId : undefined;
97
+
98
+ useEffect(() => {
99
+ setSelectedTier(featureId ? selectedTierByFeature[featureId] : undefined);
100
+ }, [featureId, selectedTierByFeature]);
102
101
 
103
102
  const handleTierChange = (tier: PriceTierFragment) => {
104
103
  const updatedTierByFeature: Record<string, PriceTierFragment> = {};
@@ -121,8 +120,7 @@ export const PlanPrice = ({
121
120
  style={{ minHeight: '20px' }}
122
121
  className="stigg-starting-at-text"
123
122
  variant="body1"
124
- color="secondary"
125
- >
123
+ color="secondary">
126
124
  {showStartingAt ? paywallLocale.price.startingAtCaption : EMPTY_CHAR}
127
125
  </Typography>
128
126
  )}
@@ -145,15 +143,14 @@ export const PlanPrice = ({
145
143
  </Typography>
146
144
  )}
147
145
 
148
- {withTiersRow && (
146
+ {withTiersRow ? (
149
147
  <TiersSelectContainer
150
148
  componentId={`${plan.id}_${featureId}_tier`}
151
149
  tiers={tiers}
152
- tierUnits={tierUnits}
153
150
  selectedTier={selectedTier}
154
151
  handleTierChange={handleTierChange}
155
152
  />
156
- )}
153
+ ) : null}
157
154
  </>
158
155
  </PlanPriceContainer>
159
156
  );
@@ -6,17 +6,19 @@ export const currencyPriceFormatter = ({
6
6
  currency = Currency.Usd,
7
7
  locale,
8
8
  maximumFractionDigits = 5,
9
+ minimumFractionDigits = 0,
9
10
  }: {
10
11
  amount: number;
11
12
  currency?: Currency | string;
12
13
  locale?: string;
13
14
  maximumFractionDigits?: number;
15
+ minimumFractionDigits?: number;
14
16
  }) => {
15
17
  const currencyString = currency.toString();
16
18
  const currencySymbol = getSymbolFromCurrency(currencyString);
17
19
  let formattedPrice = new Intl.NumberFormat(locale, {
18
- maximumFractionDigits: maximumFractionDigits,
19
- minimumFractionDigits: 0,
20
+ maximumFractionDigits,
21
+ minimumFractionDigits,
20
22
  style: 'currency',
21
23
  currency: currencyString,
22
24
  ...(currencySymbol ? { currencyDisplay: 'code' } : {}),
@@ -2,13 +2,21 @@ import { FeatureFragment } from '@stigg/api-client-js/src/generated/sdk';
2
2
  import lowercase from 'lodash/lowerCase';
3
3
 
4
4
  export function getFeatureDisplayName(feature: FeatureFragment) {
5
- const displayNameLowerCase = lowercase(feature.displayName);
5
+ return getFeatureDisplayNameText(feature.displayName, feature.featureUnits, feature.featureUnitsPlural);
6
+ }
7
+
8
+ export function getFeatureDisplayNameText(featureDisplayName: string, featureUnits: string | undefined | null, featureUnitsPlural: string | undefined | null) {
9
+ if(!featureUnits && !featureUnitsPlural) {
10
+ return featureDisplayName;
11
+ }
12
+
13
+ const displayNameLowerCase = lowercase(featureDisplayName);
6
14
  if (
7
- displayNameLowerCase === lowercase(feature.featureUnits || '') ||
8
- displayNameLowerCase === lowercase(feature.featureUnitsPlural || '')
15
+ displayNameLowerCase === lowercase(featureUnits || '') ||
16
+ displayNameLowerCase === lowercase(featureUnitsPlural || '')
9
17
  ) {
10
- return feature.displayName;
18
+ return featureDisplayName;
11
19
  }
12
20
 
13
- return `${feature.displayName} (${feature.featureUnitsPlural})`;
21
+ return `${featureDisplayName} (${featureUnitsPlural})`;
14
22
  }
@@ -4,6 +4,8 @@ import { ComponentMeta, ComponentStory } from '@storybook/react';
4
4
  import { Checkout } from '../components/checkout';
5
5
  import { StiggProvider } from '../components/StiggProvider';
6
6
  import { defaultArgsWithCustomer } from './baseArgs';
7
+ import { mockCheckoutState } from './mocks/checkout/mockCheckoutState';
8
+ import { mockPreviewSubscription } from './mocks/checkout/mockCheckoutPreview';
7
9
 
8
10
  export default {
9
11
  title: 'Stigg React SDK/Checkout',
@@ -21,6 +23,18 @@ export default {
21
23
  </StiggProvider>
22
24
  ),
23
25
  ],
26
+ parameters: {
27
+ controls: {
28
+ exclude: [
29
+ 'onCheckout',
30
+ 'onCheckoutCompleted',
31
+ 'onChangePlan',
32
+ 'onBillingAddressChange',
33
+ 'onMockCheckoutState',
34
+ 'onMockCheckoutPreview',
35
+ ],
36
+ },
37
+ },
24
38
  } as ComponentMeta<typeof Checkout>;
25
39
 
26
40
  const Wrapper = styled.div`
@@ -40,14 +54,34 @@ const Template: ComponentStory<any> = (args) => (
40
54
  }}
41
55
  onCheckout={async ({ checkoutParams, checkoutAction }) => {
42
56
  console.log('checkout started!', checkoutParams);
57
+ if (args.useMockData) {
58
+ console.log('returning mock checkout success response');
59
+ return { success: true };
60
+ }
61
+
43
62
  const { success, errorMessage } = await checkoutAction();
44
63
  return { success, errorMessage };
45
64
  }}
65
+ billableFeatures={[{ featureId: 'feature-seat', quantity: 30 }]}
46
66
  onChangePlan={({ currentPlan }) => {
47
67
  console.log('plan changed clicked!', { currentPlan });
48
68
  }}
49
- // disableSuccessAnimation
50
- // billingInformation={{ taxPercentage: 27 }}
69
+ onMockCheckoutState={
70
+ args.useMockData
71
+ ? (params) => {
72
+ console.log('mocking checkout state', params);
73
+ return mockCheckoutState(params);
74
+ }
75
+ : undefined
76
+ }
77
+ onMockCheckoutPreview={
78
+ args.useMockData
79
+ ? (params) => {
80
+ console.log('mocking checkout preview');
81
+ return mockPreviewSubscription(params);
82
+ }
83
+ : undefined
84
+ }
51
85
  />
52
86
  </Wrapper>
53
87
  );
@@ -56,8 +90,5 @@ export const DefaultCheckout = Template.bind({});
56
90
  DefaultCheckout.args = {
57
91
  ...defaultArgsWithCustomer,
58
92
  planId: 'plan-revvenu-essentials',
59
- // baseUri: 'http://localhost:4000',
60
- // apiKey: 'client-72b058a6-0f22-4c86-adce-bf266d12e12e:9f356ceb-c94c-42a4-9572-10b12824da81',
61
- baseUri: 'https://api-staging.stigg.io',
62
- apiKey: 'client-79584f52-7ef9-4c58-b9ac-5080acf492e4:71f2274c-100a-4fa4-8a43-48fa3b16c627',
93
+ useMockData: false,
63
94
  };
@@ -33,7 +33,7 @@ export default {
33
33
  }
34
34
  }
35
35
  baseUri={args.baseUri}
36
- enableEdge={args.disableEdge}>
36
+ enableEdge={!args.disableEdge}>
37
37
  <Story />
38
38
  </StiggProvider>
39
39
  ),
@@ -70,7 +70,7 @@ const Template: ComponentStory<any> = (args) => {
70
70
  onPlanSelected={(...args) => {
71
71
  console.log('onPlanSelected', args);
72
72
  }}
73
- highlightedPlanId="plan-revvenu-unity"
73
+ highlightedPlanId="plan-revvenu-essentials"
74
74
  />
75
75
  }
76
76
  theme={customerPortalTheme}
@@ -0,0 +1,15 @@
1
+ export const BASE_FEE_MONTHLY = 200;
2
+ export const BASE_FEE_YEARLY = 175 * 12;
3
+ export const TIERS = [100, 500, 750];
4
+ export const TIERS_PRICE_MONTHLY = [10, 49, 70];
5
+ export const TIERS_PRICE_YEARLY = [8, 35, 50].map((p) => p * 12);
6
+
7
+ export const PER_UNIT_PRICE_MONTHLY = 12;
8
+ export const PER_UNIT_PRICE_YEARLY = 10 * 12;
9
+
10
+ export const ADDON_PRICE_MONTHLY = 50;
11
+ export const ADDON_PRICE_YEARLY = 35 * 12;
12
+
13
+ export const STRIPE_MOCK_ACCOUNT_ID = 'acct_1NnHoQG6EyqgvTaj';
14
+ export const STRIPE_MOCK_ACCOUNT_PK =
15
+ 'pk_test_51NnHoQG6EyqgvTajznajopWC01AozNtq7zgySeQ1qx4PH9TAXvMj0TnbZvYT3yOt46jbQAcCDs1EU2QKcfG8eEoO00tlW0Jp3r';
@@ -0,0 +1,138 @@
1
+ import moment from 'moment';
2
+ import {
3
+ BillingPeriod,
4
+ BillingModel,
5
+ Currency,
6
+ BillableFeature,
7
+ DateRange,
8
+ Money,
9
+ Plan,
10
+ PreviewSubscription,
11
+ SubscriptionEstimationAddon,
12
+ SubscriptionPreviewV2,
13
+ } from '@stigg/js-client-sdk';
14
+ import { mockCheckoutState } from './mockCheckoutState';
15
+
16
+ const mockBillingPeriod = (period?: BillingPeriod): DateRange => {
17
+ return {
18
+ start: moment().toDate(),
19
+ end: moment()
20
+ .add(1, period === BillingPeriod.Monthly ? 'month' : 'year')
21
+ .toDate(),
22
+ };
23
+ };
24
+
25
+ const defaultPreviewSubscription = (): SubscriptionPreviewV2 => {
26
+ const defaultCost: Money = {
27
+ amount: 0,
28
+ currency: Currency.Usd,
29
+ };
30
+
31
+ return {
32
+ subTotal: defaultCost,
33
+ total: defaultCost,
34
+ totalExcludingTax: defaultCost,
35
+ billingPeriodRange: mockBillingPeriod(),
36
+ };
37
+ };
38
+
39
+ const flatFeeCost = (plan: Plan, billingPeriod: BillingPeriod | undefined) => {
40
+ const filteredPrice = plan.pricePoints?.find(
41
+ (price) => price.billingPeriod === billingPeriod && price.pricingModel === BillingModel.FlatFee,
42
+ );
43
+
44
+ return filteredPrice?.amount || 0;
45
+ };
46
+
47
+ const addonCost = (plan: Plan, billingPeriod: BillingPeriod, addonId: string, quantity: number) => {
48
+ const addon = plan.compatibleAddons?.find((addon) => addon.id === addonId);
49
+
50
+ const price = addon?.pricePoints.find((price) => price.billingPeriod === billingPeriod);
51
+
52
+ return (price?.amount || 0) * quantity;
53
+ };
54
+
55
+ const billableFeatureCost = (plan: Plan, billingPeriod: BillingPeriod, featureId: string, quantity: number) => {
56
+ const price = plan.pricePoints.find(
57
+ (price) => price.feature?.featureId === featureId && price.billingPeriod === billingPeriod,
58
+ );
59
+
60
+ if (!price) return 0;
61
+
62
+ const { tiers } = price;
63
+
64
+ if (tiers) {
65
+ const quantityTier = tiers.find((tier) => tier.upTo >= quantity);
66
+ const priceTier = quantityTier || tiers[tiers.length - 1];
67
+ return quantity * priceTier.unitPrice.amount;
68
+ }
69
+
70
+ return (price?.amount || 0) * quantity;
71
+ };
72
+
73
+ const mockTotalPrice = (
74
+ plan: Plan,
75
+ billingPeriod: BillingPeriod,
76
+ addons: SubscriptionEstimationAddon[],
77
+ features: BillableFeature[],
78
+ ) => {
79
+ const currency = plan.pricePoints?.[0].currency || Currency.Usd;
80
+
81
+ const totalFlatFeeCost = flatFeeCost(plan, billingPeriod);
82
+ const totalFeaturesCost = features.reduce(
83
+ (total, feature) => total + billableFeatureCost(plan, billingPeriod, feature.featureId, feature.quantity || 0),
84
+ 0,
85
+ );
86
+ const totalAddonsCost = addons.reduce(
87
+ (total, addon) => total + addonCost(plan, billingPeriod, addon.addonId, addon.quantity || 0),
88
+ 0,
89
+ );
90
+
91
+ const cost: Money = {
92
+ amount: totalFlatFeeCost + totalFeaturesCost + totalAddonsCost,
93
+ currency: currency || Currency.Usd,
94
+ };
95
+
96
+ return {
97
+ subTotal: cost,
98
+ total: cost,
99
+ totalExcludingTax: cost,
100
+ };
101
+ };
102
+
103
+ export function mockPreviewSubscription(input: PreviewSubscription): SubscriptionPreviewV2 {
104
+ const {
105
+ planId,
106
+ billingPeriod = BillingPeriod.Monthly,
107
+ billableFeatures: features = [],
108
+ addons = [],
109
+ promotionCode,
110
+ } = input;
111
+
112
+ if (promotionCode) {
113
+ throw new Error('Error: Invalid promotion code');
114
+ }
115
+
116
+ const data = mockCheckoutState({ planId });
117
+
118
+ if (!data || !data.plan) {
119
+ return defaultPreviewSubscription();
120
+ }
121
+
122
+ const total = mockTotalPrice(data.plan, billingPeriod, addons, features);
123
+
124
+ if (!total) {
125
+ return defaultPreviewSubscription();
126
+ }
127
+
128
+ return {
129
+ ...total,
130
+ billingPeriodRange: mockBillingPeriod(billingPeriod),
131
+ proration: {
132
+ prorationDate: moment().toDate(),
133
+ credit: total.total,
134
+ debit: total.total,
135
+ netAmount: total.total,
136
+ },
137
+ };
138
+ }
@@ -0,0 +1,206 @@
1
+ import moment from 'moment';
2
+ import { camelCase, startCase } from 'lodash';
3
+ import {
4
+ BillingModel,
5
+ BillingPeriod,
6
+ BillingVendorIdentifier,
7
+ Currency,
8
+ PricingType,
9
+ TiersMode,
10
+ CheckoutStatePlan,
11
+ Customer,
12
+ GetCheckoutState,
13
+ GetCheckoutStateResults,
14
+ Price,
15
+ Product,
16
+ PromotionalEntitlement,
17
+ Subscription,
18
+ Addon,
19
+ } from '../../../../../js-client-sdk';
20
+ import {
21
+ BASE_FEE_MONTHLY,
22
+ TIERS_PRICE_MONTHLY,
23
+ PER_UNIT_PRICE_MONTHLY,
24
+ PER_UNIT_PRICE_YEARLY,
25
+ STRIPE_MOCK_ACCOUNT_ID,
26
+ STRIPE_MOCK_ACCOUNT_PK,
27
+ TIERS,
28
+ BASE_FEE_YEARLY,
29
+ TIERS_PRICE_YEARLY,
30
+ ADDON_PRICE_MONTHLY,
31
+ ADDON_PRICE_YEARLY,
32
+ } from './consts';
33
+
34
+ const mockCustomer: Customer = {
35
+ id: '462d5d8a-22c4-4f22-9306-38d1a3047675',
36
+ name: 'John Doe',
37
+ email: 'john.doe@example.com',
38
+ createdAt: moment().subtract(1, 'year').toDate(),
39
+ updatedAt: moment().subtract(1, 'month').toDate(),
40
+ hasPaymentMethod: false,
41
+ promotionalEntitlements: [],
42
+ subscriptions: [],
43
+ getActivePromotionalEntitlements(): PromotionalEntitlement[] {
44
+ return [];
45
+ },
46
+ getActiveSubscriptions(): Subscription[] {
47
+ return [];
48
+ },
49
+ getActiveTrials(): Subscription[] {
50
+ return [];
51
+ },
52
+ };
53
+
54
+ const mockProduct: Product = {
55
+ id: 'product-1',
56
+ displayName: 'Product 1',
57
+ description: 'Product 1 description',
58
+ };
59
+
60
+ const additionalStorageAddons: Addon = {
61
+ id: 'addon-additional-storage',
62
+ description: 'Additional storage',
63
+ displayName: 'Additional storage',
64
+ entitlements: [],
65
+ pricePoints: [
66
+ {
67
+ pricingModel: BillingModel.FlatFee,
68
+ billingPeriod: BillingPeriod.Monthly,
69
+ amount: ADDON_PRICE_MONTHLY,
70
+ currency: Currency.Usd,
71
+ tiersMode: undefined,
72
+ isTieredPrice: false,
73
+ },
74
+ {
75
+ pricingModel: BillingModel.FlatFee,
76
+ billingPeriod: BillingPeriod.Annually,
77
+ amount: ADDON_PRICE_YEARLY,
78
+ currency: Currency.Usd,
79
+ tiersMode: undefined,
80
+ isTieredPrice: false,
81
+ },
82
+ ],
83
+ };
84
+
85
+ const flatFeePricing: Price[] = [
86
+ {
87
+ pricingModel: BillingModel.FlatFee,
88
+ billingPeriod: BillingPeriod.Monthly,
89
+ amount: BASE_FEE_MONTHLY,
90
+ currency: Currency.Usd,
91
+ tiersMode: undefined,
92
+ isTieredPrice: false,
93
+ },
94
+ {
95
+ pricingModel: BillingModel.FlatFee,
96
+ billingPeriod: BillingPeriod.Annually,
97
+ amount: BASE_FEE_YEARLY,
98
+ currency: Currency.Usd,
99
+ tiersMode: undefined,
100
+ isTieredPrice: false,
101
+ },
102
+ ];
103
+
104
+ function tieredPricing(): Price[] {
105
+ const feature = {
106
+ featureId: 'feature-campaigns',
107
+ displayName: 'Campaigns per month',
108
+ units: 'campaign',
109
+ unitsPlural: 'campaigns',
110
+ };
111
+
112
+ return [
113
+ {
114
+ pricingModel: BillingModel.PerUnit,
115
+ billingPeriod: BillingPeriod.Monthly,
116
+ tiersMode: TiersMode.Volume,
117
+ tiers: TIERS.map((tier, index) => ({
118
+ upTo: tier,
119
+ unitPrice: {
120
+ amount: TIERS_PRICE_MONTHLY[index] / tier,
121
+ currency: Currency.Usd,
122
+ },
123
+ })),
124
+ feature,
125
+ currency: Currency.Usd,
126
+ isTieredPrice: true,
127
+ },
128
+ {
129
+ pricingModel: BillingModel.PerUnit,
130
+ billingPeriod: BillingPeriod.Annually,
131
+ tiersMode: TiersMode.Volume,
132
+ tiers: TIERS.map((tier, index) => ({
133
+ upTo: tier,
134
+ unitPrice: {
135
+ amount: TIERS_PRICE_YEARLY[index] / tier,
136
+ currency: Currency.Usd,
137
+ },
138
+ })),
139
+ feature,
140
+ currency: Currency.Usd,
141
+ isTieredPrice: true,
142
+ },
143
+ ];
144
+ }
145
+
146
+ function perUnitPricing(): Price[] {
147
+ const feature = {
148
+ featureId: 'feature-seats',
149
+ displayName: 'Seats',
150
+ units: 'seat',
151
+ unitsPlural: 'seats',
152
+ };
153
+
154
+ return [
155
+ {
156
+ pricingModel: BillingModel.PerUnit,
157
+ billingPeriod: BillingPeriod.Monthly,
158
+ amount: PER_UNIT_PRICE_MONTHLY,
159
+ currency: Currency.Usd,
160
+ feature,
161
+ tiersMode: undefined,
162
+ isTieredPrice: false,
163
+ },
164
+ {
165
+ pricingModel: BillingModel.PerUnit,
166
+ billingPeriod: BillingPeriod.Annually,
167
+ amount: PER_UNIT_PRICE_YEARLY,
168
+ currency: Currency.Usd,
169
+ feature,
170
+ tiersMode: undefined,
171
+ isTieredPrice: false,
172
+ },
173
+ ];
174
+ }
175
+
176
+ function mockPlan(planRefId: string): CheckoutStatePlan {
177
+ return {
178
+ id: '4b6c639e-1100-4ae1-86a9-31324994f992',
179
+ displayName: startCase(camelCase(planRefId)),
180
+ pricingType: PricingType.Paid,
181
+ pricePoints: [...flatFeePricing, ...perUnitPricing(), ...tieredPricing()],
182
+ product: mockProduct,
183
+ order: 0,
184
+ compatibleAddons: [additionalStorageAddons],
185
+ entitlements: [],
186
+ inheritedEntitlements: [],
187
+ };
188
+ }
189
+
190
+ export function mockCheckoutState(params: GetCheckoutState): GetCheckoutStateResults {
191
+ const { planId } = params;
192
+
193
+ return {
194
+ setupSecret: '',
195
+ customer: mockCustomer,
196
+ plan: mockPlan(planId),
197
+ billingIntegration: {
198
+ billingIdentifier: BillingVendorIdentifier.Stripe,
199
+ credentials: {
200
+ accountId: STRIPE_MOCK_ACCOUNT_ID,
201
+ publicKey: STRIPE_MOCK_ACCOUNT_PK,
202
+ },
203
+ },
204
+ resource: null,
205
+ };
206
+ }
@@ -61,13 +61,22 @@ function createTypographyTheme(theme: StiggTheme): Partial<TypographyProps> {
61
61
  };
62
62
  }
63
63
 
64
+ const createMuiPalette = (theme: StiggTheme) => {
65
+ return {
66
+ primary: {
67
+ main: theme.palette.primary,
68
+ },
69
+ };
70
+ };
71
+
64
72
  export const SdkThemeProvider: React.FC<PropsWithChildren<SdkThemeProviderProps>> = ({ children, componentTheme }) => {
65
73
  const theme = useStiggTheme(componentTheme);
74
+ const muiPalette = createMuiPalette(theme);
66
75
 
67
76
  return (
68
77
  // We are using styled-components theme here only because we are using styled-typography
69
78
  // which depends on styled-components for the typography theming
70
- <MuiThemeProvider theme={createTheme({ stigg: theme })}>
79
+ <MuiThemeProvider theme={createTheme({ palette: muiPalette, stigg: theme })}>
71
80
  <ThemeProvider theme={{ stigg: theme }}>
72
81
  <CustomCssGlobal customCss={theme.customCss}>
73
82
  <Fonts externalFontUrl={theme.typography.fontFamilyUrl} />
@@ -21,6 +21,7 @@ export const getResolvedTheme = (customizedTheme?: CustomizedTheme): StiggTheme
21
21
  palette: {
22
22
  primary: primaryColor.hex(),
23
23
  primaryDark: primaryColor.darken(0.3).hex(),
24
+ primaryLight: primaryColor.lighten(0.6).hex(),
24
25
  backgroundPaper: '#FFFFFF',
25
26
  backgroundHighlight: '#F5F6F9',
26
27
  backgroundSection: primaryColor.alpha(0.1).toString(),
@@ -9,6 +9,7 @@ export type StiggTheme = {
9
9
  palette: {
10
10
  primary: string;
11
11
  primaryDark: string;
12
+ primaryLight: string;
12
13
  backgroundPaper: string;
13
14
  backgroundHighlight: string;
14
15
  backgroundSection: string;