diff --git a/README.md b/README.md index e9682ee8..46c80d9b 100644 --- a/README.md +++ b/README.md @@ -149,6 +149,10 @@ The `createWidget` function accepts an object with the following properties: * @default false */ showGiftCardOption?: boolean; + /** + * Partner webhook token + */ + webhookToken?: string; } ``` diff --git a/packages/donate-button-v4/src/components/widget/components/PaymentProcess/GiftCardFlow/index.tsx b/packages/donate-button-v4/src/components/widget/components/PaymentProcess/GiftCardFlow/index.tsx index f10a543b..3a641370 100644 --- a/packages/donate-button-v4/src/components/widget/components/PaymentProcess/GiftCardFlow/index.tsx +++ b/packages/donate-button-v4/src/components/widget/components/PaymentProcess/GiftCardFlow/index.tsx @@ -1,3 +1,4 @@ +import cxs from 'cxs'; import {giftCardIconCss} from 'src/components/widget/components/PaymentProcess/GiftCardFlow/styles'; import { LargePaymentMethodSelect, @@ -9,13 +10,19 @@ import { formCss, formContainerCss } from 'src/components/widget/components/PaymentProcess/styles'; +import {TextInput} from 'src/components/widget/components/TextInput'; +import {useConfigContext} from 'src/components/widget/hooks/useConfigContext'; import {useSubmitDonation} from 'src/components/widget/hooks/useSubmitDonation'; +import {useWidgetContext} from 'src/components/widget/hooks/useWidgetContext'; import {GiftIcon} from 'src/components/widget/icons/GiftIcon'; +import {textSize} from 'src/components/widget/theme/font-sizes'; import {PaymentMethod} from 'src/components/widget/types/PaymentMethod'; import {getSubmitButtonText} from 'src/helpers/getSubmitButtonText'; export const GiftCardFlow = () => { const submitDonation = useSubmitDonation(); + const {redeemGiftCardInFlow} = useConfigContext(); + const {giftCardCode, setGiftCardCode} = useWidgetContext(); return (
@@ -24,6 +31,16 @@ export const GiftCardFlow = () => {

Redeem a gift card to add donation credits to your account.

+ {redeemGiftCardInFlow && ( + { + setGiftCardCode(event.currentTarget.value); + }} + /> + )} {getSubmitButtonText({method: PaymentMethod.GIFT_CARD})} @@ -32,3 +49,9 @@ export const GiftCardFlow = () => { ); }; + +export const giftCardCodeInputCss = cxs({ + fontSize: textSize.l.fontSize, + lineHeight: textSize.l.fontSize, + fontWeight: 700 +}); diff --git a/packages/donate-button-v4/src/components/widget/context/WidgetContext.tsx b/packages/donate-button-v4/src/components/widget/context/WidgetContext.tsx index 0ac51f7c..2763aeb7 100644 --- a/packages/donate-button-v4/src/components/widget/context/WidgetContext.tsx +++ b/packages/donate-button-v4/src/components/widget/context/WidgetContext.tsx @@ -39,6 +39,9 @@ interface WidgetContextProps { privateNote?: string; setPrivateNote: StateUpdater; + + giftCardCode?: string; + setGiftCardCode: StateUpdater; } export const WidgetContext = createContext( @@ -70,6 +73,8 @@ export const WidgetContextProvider: FunctionalComponent<{hide: () => void}> = ({ const [privateNote, setPrivateNote] = useState(); + const [giftCardCode, setGiftCardCode] = useState(); + return ( void}> = ({ setCryptoCurrency, paymentRequestAvailable, privateNote, - setPrivateNote + setPrivateNote, + giftCardCode, + setGiftCardCode }} > {children} diff --git a/packages/donate-button-v4/src/components/widget/hooks/useSubmitDonation.ts b/packages/donate-button-v4/src/components/widget/hooks/useSubmitDonation.ts index 33e9dc87..8ac44bbf 100644 --- a/packages/donate-button-v4/src/components/widget/hooks/useSubmitDonation.ts +++ b/packages/donate-button-v4/src/components/widget/hooks/useSubmitDonation.ts @@ -4,6 +4,7 @@ import {useConfigContext} from 'src/components/widget/hooks/useConfigContext'; import {useWidgetContext} from 'src/components/widget/hooks/useWidgetContext'; import {DonationFrequency} from 'src/components/widget/types/DonationFrequency'; import { + AvailablePaymentMethods, OneTimeFrequencyMethods, PaymentMethod } from 'src/components/widget/types/PaymentMethod'; @@ -27,9 +28,11 @@ export const useSubmitDonation = () => { stockSymbol, cryptoAmount, cryptoCurrency, - privateNote + privateNote, + giftCardCode } = useWidgetContext(); - const {minDonationAmount} = useConfigContext(); + const {minDonationAmount, webhookToken, redeemGiftCardInFlow} = + useConfigContext(); const submitDonation = useCallback( (event: JSXInternal.TargetedEvent) => { @@ -42,7 +45,8 @@ export const useSubmitDonation = () => { nonprofitSlug: config.nonprofitSlug, fundraiserSlug: config.fundraiserSlug, utmSource: config.utmSource, - privateNote + privateNote, + webhookToken }; switch (selectedPaymentMethod) { case PaymentMethod.CRYPTO: @@ -76,7 +80,15 @@ export const useSubmitDonation = () => { ); break; case PaymentMethod.GIFT_CARD: - window.open(constructGiftCardUrl(config.nonprofitSlug), target); + window.open( + constructGiftCardUrl({ + redeemGiftCardInFlow, + giftCardCode, + ...baseParameters, + methods: undefined + }), + target + ); break; default: if (!donationAmount || donationAmount < minDonationAmount) { @@ -110,7 +122,10 @@ export const useSubmitDonation = () => { stockSymbol, cryptoAmount, cryptoCurrency, - privateNote + privateNote, + giftCardCode, + webhookToken, + redeemGiftCardInFlow ] ); diff --git a/packages/donate-button-v4/src/components/widget/types/WidgetConfig.ts b/packages/donate-button-v4/src/components/widget/types/WidgetConfig.ts index a889e822..97cd9fe4 100644 --- a/packages/donate-button-v4/src/components/widget/types/WidgetConfig.ts +++ b/packages/donate-button-v4/src/components/widget/types/WidgetConfig.ts @@ -33,4 +33,8 @@ export interface WidgetConfig { showGiftCardOption?: boolean; utmSource?: string; + + webhookToken?: string; + + redeemGiftCardInFlow?: boolean; } diff --git a/packages/donate-button-v4/src/helpers/constructDonateUrl.ts b/packages/donate-button-v4/src/helpers/constructDonateUrl.ts index 16c4cbfb..33bb1b7c 100644 --- a/packages/donate-button-v4/src/helpers/constructDonateUrl.ts +++ b/packages/donate-button-v4/src/helpers/constructDonateUrl.ts @@ -1,6 +1,9 @@ /* eslint-disable unicorn/prevent-abbreviations */ import {DonationFrequency} from 'src/components/widget/types/DonationFrequency'; -import {PaymentMethod} from 'src/components/widget/types/PaymentMethod'; +import { + AvailablePaymentMethods, + PaymentMethod +} from 'src/components/widget/types/PaymentMethod'; import {BASE_URL, GIFT_CARD_URL} from 'src/constants/url'; const UTM_MEDIUM = 'donate-button-0.4'; // Update this if the major version changes @@ -14,6 +17,7 @@ interface BaseUrlParams { methods?: PaymentMethod[]; privateNote?: string; utmSource?: string; + webhookToken?: string; } interface DonateUrlParams extends BaseUrlParams { @@ -31,6 +35,11 @@ interface DonateCryptoUrlParams extends BaseUrlParams { cryptoCurrency: string; } +interface GiftCardUrlParams extends BaseUrlParams { + giftCardCode?: string; + redeemGiftCardInFlow?: boolean; +} + function serializeParams( params: Record ) { @@ -58,10 +67,16 @@ function getBaseParams({ nonprofitSlug, noExit, privateNote, - utmSource + utmSource, + webhookToken }: Pick< BaseUrlParams, - 'nonprofitSlug' | 'methods' | 'noExit' | 'privateNote' | 'utmSource' + | 'nonprofitSlug' + | 'methods' + | 'noExit' + | 'privateNote' + | 'utmSource' + | 'webhookToken' >) { return { method: methods?.join(','), @@ -69,7 +84,8 @@ function getBaseParams({ utm_source: utmSource ?? nonprofitSlug, utm_medium: UTM_MEDIUM, no_exit: noExit ?? 1, - private_note: privateNote + private_note: privateNote, + webhook_token: webhookToken }; } @@ -136,9 +152,25 @@ export function constructDonateCryptoUrl({ return `${baseUrl}?${parameters}#/${HASH}`; } -export function constructGiftCardUrl(nonprofitSlug: string) { +export function constructGiftCardUrl({ + redeemGiftCardInFlow, + giftCardCode, + ...rest +}: GiftCardUrlParams) { + if (redeemGiftCardInFlow) { + const baseUrl = getBaseUrl(rest); + const params = getBaseParams(rest); + + const parameters = serializeParams({ + ...params, + gift_card_code: giftCardCode + }); + + return `${baseUrl}?${parameters}#/${HASH}`; + } + const parameters = serializeParams({ - nonprofitSlug + nonprofitSlug: rest.nonprofitSlug }); return `${GIFT_CARD_URL}?${parameters}`; diff --git a/packages/donate-button-v4/src/helpers/optionsTypes.ts b/packages/donate-button-v4/src/helpers/optionsTypes.ts index e54dadc3..0c78e0b9 100644 --- a/packages/donate-button-v4/src/helpers/optionsTypes.ts +++ b/packages/donate-button-v4/src/helpers/optionsTypes.ts @@ -14,7 +14,8 @@ const defaults: Partial = { defaultFrequency: DonationFrequency.OneTime, minDonationAmount: 5, primaryColor: '#018669', - showGiftCardOption: false + showGiftCardOption: false, + redeemGiftCardInFlow: false }; const DEEP_MERGE_OPTIONS: DeepMergeOptions = {